Урок 8.5 — Интеграция с Telethon
Учимся интегрировать aiosend с Telethon — асинхронной библиотекой для MTProto с богатыми возможностями обработки событий.
Telethon — ещё одна асинхронная MTProto-библиотека для Python. Она предоставляет богатую систему событий через @client.on(). Интеграция с aiosend строится по тому же принципу, что и с Pyrogram: обе библиотеки асинхронные, запускаем параллельно.
Параллельный запуск Telethon + aiosend
Telethon использует @client.on(events.NewMessage) для обработки сообщений. Запускается через client.start() и client.run_until_disconnected().
import asyncio
from telethon import TelegramClient, events
from aiosend import CryptoPay
BOT_TOKEN = "123456:ABCdefGHIjklmNOP"
CP_TOKEN = "1234:ABCDefGHIJklmnOPQRST"
API_ID = 12345
API_HASH = "0123456789abcdef0123456789abcdef"
client = TelegramClient("bot", API_ID, API_HASH).start(bot_token=BOT_TOKEN)
cp = CryptoPay(token=CP_TOKEN)
@client.on(events.NewMessage(pattern="/start"))
async def start(event):
await event.reply(
"Привет! Я бот на Telethon + aiosend!\n"
"Используй /pay 10 USDT для оплаты."
)
@client.on(events.NewMessage(pattern="/pay"))
async def pay(event):
text = event.message.text
parts = text.split()
if len(parts) < 3:
await event.reply("Пример: /pay 10 USDT")
return
amount, asset = float(parts[1]), parts[2].upper()
invoice = await cp.create_invoice(
amount=amount,
asset=asset,
payload=str(event.sender_id),
)
await event.reply(
f"🧾 Счёт на {amount} {asset}:\n"
f"{invoice.bot_invoice_url}"
)
@cp.invoice_paid()
async def on_paid(invoice):
user_id = int(invoice.payload)
await client.send_message(
user_id,
f"✅ Оплата {invoice.amount} {invoice.asset} получена!",
)
async def main():
await asyncio.gather(
client.run_until_disconnected(),
cp.start_polling(),
)
asyncio.run(main())
💡 Особенность Telethon
Telethon не требует отдельного вызова client.start() в асинхронном коде, если использовать TelegramClient("bot", API_ID, API_HASH).start(bot_token=TOKEN). Но client.start() можно вызвать и отдельно как корутину.
Система событий Telethon
Telethon использует богатую систему событий. Можно фильтровать по тексту, отправителю, чату и другим параметрам.
from telethon import events
# По команде
@client.on(events.NewMessage(pattern="/buy"))
async def buy(event):
invoice = await cp.create_invoice(
amount=10, asset="USDT",
payload=str(event.sender_id),
)
msg = await event.reply(
f"💳 Счёт: {invoice.bot_invoice_url}"
)
# Ожидаем оплату
paid = await invoice.poll(message=msg)
await msg.edit(f"✅ Оплачено: {paid.paid_amount} {paid.paid_asset}")
# Только личные сообщения
@client.on(events.NewMessage(pattern="/admin", from_users=ADMIN_ID))
async def admin(event):
await event.reply("Панель администратора")
# Callback-запросы
@client.on(events.CallbackQuery())
async def callback(event):
data = event.data.decode()
if data.startswith("buy_"):
# Обработка покупки
await event.answer("Создаю счёт...")
🔍 События Telethon
events.NewMessage— новое сообщениеevents.CallbackQuery— нажатие на inline-кнопкуevents.MessageEdited— редактирование сообщенияevents.UserUpdate— обновление пользователя- Фильтры:
pattern,from_users,chats,incoming,outgoing
Полный пример: магазин на Telethon
import asyncio
from telethon import TelegramClient, events
from telethon.tl.types import InlineKeyboardButton, InlineKeyboardMarkup
from aiosend import CryptoPay
BOT_TOKEN = "123456:ABCdefGHIjklmNOP"
CP_TOKEN = "1234:ABCDefGHIJklmnOPQRST"
API_ID = 12345
API_HASH = "0123456789abcdef0123456789abcdef"
client = TelegramClient("shop", API_ID, API_HASH).start(bot_token=BOT_TOKEN)
cp = CryptoPay(token=CP_TOKEN)
PRODUCTS = {
"premium": {"name": "Премиум", "price": 15, "asset": "USDT"},
"vip": {"name": "VIP-доступ", "price": 50, "asset": "USDT"},
}
@client.on(events.NewMessage(pattern="/start"))
async def start(event):
kb = InlineKeyboardMarkup([[
InlineKeyboardButton("💎 Премиум", data=b"buy_premium"),
InlineKeyboardButton("⭐ VIP", data=b"buy_vip"),
]])
await event.reply("🛒 Добро пожаловать!", buttons=kb)
@client.on(events.CallbackQuery())
async def callback(event):
data = event.data.decode()
if not data.startswith("buy_"):
return
product_key = data.replace("buy_", "")
product = PRODUCTS.get(product_key)
if not product:
await event.answer("Товар не найден")
return
await event.answer("Создаём счёт...")
invoice = await cp.create_invoice(
amount=product["price"],
asset=product["asset"],
description=product["name"],
payload=f"{event.sender_id}:{product_key}",
)
msg = await event.reply(
f"💳 {product['name']}\n"
f"Сумма: {product['price']} {product['asset']}\n\n"
f"🔗 {invoice.bot_invoice_url}\n\n"
f"⏳ Ожидаем оплату...",
parse_mode="html",
)
try:
paid = await invoice.poll(message=msg)
await msg.edit(
f"✅ Оплачено!\n"
f"{paid.paid_amount} {paid.paid_asset}\n"
f"Товар: {product['name']}",
parse_mode="html",
)
except Exception as e:
await msg.edit(f"❌ Ошибка: {e}")
@cp.invoice_paid()
async def on_paid(invoice):
user_id, product_key = invoice.payload.split(":")
product = PRODUCTS.get(product_key, {"name": "товар"})
print(f"Платёж: user={user_id} product={product['name']}")
await client.send_message(
int(user_id),
f"✅ {product['name']} активирован! Спасибо!",
)
async def main():
await asyncio.gather(
client.run_until_disconnected(),
cp.start_polling(),
)
asyncio.run(main())
🔍 Ключевые особенности Telethon
@client.on(events.NewMessage(pattern="/cmd"))— декораторawait event.reply()— ответ на сообщениеevent.sender_id— ID отправителяawait msg.edit()— редактирование сообщения- InlineKeyboardButton принимает
dataкак байты (b"data") event.answer()— ответ на callback (всплывающее уведомление)
Что важно запомнить
Практическое задание
Задание: Donate-бот на Telethon
Создай бота на Telethon + aiosend:
- По команде /donate [сумма] [валюта] создаёт инвойс
- Отправляет ссылку на оплату
- Ожидает оплату через invoice.poll(message=msg)
- Благодарит пользователя после оплаты
- Запускает через asyncio.gather()
Подсказка:
import asyncio
from telethon import TelegramClient, events
from aiosend import CryptoPay
client = TelegramClient("bot", API_ID, API_HASH).start(bot_token="BOT_TOKEN")
cp = CryptoPay(token="CP_TOKEN")
@client.on(events.NewMessage(pattern="/donate"))
async def donate(event):
parts = event.message.text.split()
amount, asset = float(parts[1]), parts[2].upper()
invoice = await cp.create_invoice(
amount=amount, asset=asset,
payload=str(event.sender_id),
)
msg = await event.reply(f"💛 {invoice.bot_invoice_url}")
paid = await invoice.poll(message=msg)
await msg.edit(f"✅ Спасибо за {paid.paid_amount} {paid.paid_asset}!")
async def main():
await asyncio.gather(
client.run_until_disconnected(),
cp.start_polling(),
)
asyncio.run(main())
Урок 8.5: Интеграция с Telethon
5 вопросов