# Телеграмм интеграция для Django Позволяет управлять чат-ботами из админки. В окружении понимается свой локальный инстанс телеграмм сервера, на который нужно настроить pyTelegramBotAPI. Из интерфейса админки нужно дать администратору публиковать ботов, отзывать ботов и настраивать их на обслуживание интерфейсов. Интерфейс бота это класс определяющий поведение бота. Тут в пакете следует реализовать базовые классы и методы и реализовать программный апи, я предполагаю класс, который будут наследовать в других приложениях, в данном случае в App и там уже писать конкретно что бот делает, какие команды принимает и какие методы их обслуживают. Смена интерфейса бота в админке переключает поведение бота в рантайме. В первой итерации нужно реализовать поддержку создания интерфейсов чат-ботов. Которые сообщениями отвечают на сообщения. И поддержку приватных сообщений только. Но мы подразумеваем что в будущем это приложение может быть расширено. ## Как устроено Зависимости: Django и pyTelegramBotAPI. Приложение ничего не знает о других приложениях проекта: оно предоставляет базовый класс интерфейса, а приложения регистрируют свои интерфейсы сами. - `models.py` - `Bot`, `User`, `Chat` (у каждого чата состояние диалога `state` и данные `data`), `Message`. - `interfaces.py` - базовый класс `Interface`, декораторы `command`, `text`, `state` и реестр `register`. - `context.py` - `Context`, который получает обработчик: текст, команда, собеседник, состояние, `reply()`. - `messages.py` - `send()` для отправки сообщения в чат вне обработчика, например уведомления из фоновой задачи. - `dispatcher.py` - разбор обновления: сохраняет пользователя, чат, сообщение и передает его интерфейсу бота. - `runner.py` - long polling: по потоку на каждый опубликованный бот, супервизор сверяется с базой каждые 5 секунд. ## Интерфейс бота ```python from Telegram.interfaces import Interface, command, register, state, text @register class Shop(Interface): title = 'Магазин' @command('start') @text('главное меню') def menu(self, ctx): ctx.reset() ctx.reply('Привет', keyboard=[['адрес']]) @text('адрес') def ask_address(self, ctx): ctx.state = 'await_address' ctx.reply('Пришли адрес', keyboard=[['главное меню']]) @state('await_address') def address(self, ctx): ctx.data['address'] = ctx.text ctx.state = '' ctx.reply('Сохранил') @text('отмена', state='await_address') def cancel_address(self, ctx): ctx.state = '' ctx.reply('Отменил') def fallback(self, ctx): ctx.reply('Не понял') ``` Порядок разбора сообщения: команда, кнопка текущего состояния (`@text(..., state=...)`), кнопка, состояние диалога, `fallback`. `ctx.delete_message()` удаляет входящее сообщение из чата, например с паролем. Модуль с интерфейсом нужно импортировать при старте, например в `AppConfig.ready()`. ## Запуск 1. В админке добавить бота с токеном и выбрать интерфейс. 2. Действие "Опубликовать" проверяет токен, подтягивает имя бота и включает бота. "Отозвать" выключает. Если задан `TELEGRAM_API_URL`, при первой публикации бот отключается от облачного API (`logOut`). Вернуть его в облако можно не раньше чем через 10 минут. 3. `make tg_run` запускает раннер. Смена интерфейса, публикация и отзыв применяются без перезапуска. `TELEGRAM_API_URL` направляет бота на свой Bot API сервер (сервис `telegram` в `docker-compose.yaml`).