Переход на Google Style Docstring
This commit is contained in:
parent
1400f72cd0
commit
af4c9dc487
370
maxapi/bot.py
370
maxapi/bot.py
@ -23,7 +23,6 @@ from .methods.delete_bot_from_chat import DeleteMeFromMessage
|
||||
from .methods.delete_chat import DeleteChat
|
||||
from .methods.delete_message import DeleteMessage
|
||||
from .methods.delete_pin_message import DeletePinMessage
|
||||
# from .methods.download_media import DownloadMedia
|
||||
from .methods.edit_chat import EditChat
|
||||
from .methods.edit_message import EditMessage
|
||||
from .methods.get_chat_by_id import GetChatById
|
||||
@ -82,7 +81,8 @@ if TYPE_CHECKING:
|
||||
|
||||
class Bot(BaseConnection):
|
||||
|
||||
"""Основной класс для работы с API бота.
|
||||
"""
|
||||
Основной класс для работы с API бота.
|
||||
|
||||
Предоставляет методы для взаимодействия с чатами, сообщениями,
|
||||
пользователями и другими функциями бота.
|
||||
@ -100,19 +100,20 @@ class Bot(BaseConnection):
|
||||
):
|
||||
|
||||
"""
|
||||
Инициализирует экземпляр бота с указанным токеном.
|
||||
Инициализирует экземпляр бота.
|
||||
|
||||
Args:
|
||||
token (str): Токен доступа к API бота.
|
||||
parse_mode (Optional[ParseMode]): Форматирование по умолчанию.
|
||||
notify (Optional[bool]): Отключение уведомлений при отправке сообщений.
|
||||
auto_requests (bool): Автоматическое заполнение chat/from_user через API (по умолчанию True).
|
||||
default_connection (Optional[DefaultConnectionProperties]): Настройки соединения.
|
||||
after_input_media_delay (Optional[float]): Задержка после загрузки файла.
|
||||
auto_check_subscriptions (bool): Проверка подписок для метода start_polling.
|
||||
|
||||
:param token: Токен доступа к API бота
|
||||
:param parse_mode: Форматирование по умолчанию
|
||||
:param notify: Отключение уведомлений при отправке сообщений (по умолчанию игнорируется) (не работает на стороне MAX)
|
||||
:param auto_requests: Автоматическое заполнение полей chat и from_user в Update с помощью API запросов если они не заложены как полноценные объекты в Update (по умолчанию True, при False chat и from_user в некоторых событиях будут выдавать None)
|
||||
:param default_connection: Настройки aiohttp
|
||||
:param after_input_media_delay: Задержка в секундах после загрузки файла на сервера MAX (без этого чаще всего MAX не успевает обработать вложение и выдает ошибку `errors.process.attachment.file.not.processed`)
|
||||
:param auto_check_subscriptions: Проверка на установленные подписки для метода start_polling (бот не работает в поллинге при установленных подписках)
|
||||
"""
|
||||
|
||||
super().__init__()
|
||||
|
||||
self.bot = self
|
||||
self.default_connection = default_connection or DefaultConnectionProperties()
|
||||
self.after_input_media_delay = after_input_media_delay or 2.0
|
||||
@ -130,15 +131,53 @@ class Bot(BaseConnection):
|
||||
|
||||
@property
|
||||
def me(self):
|
||||
|
||||
"""
|
||||
Возвращает объект пользователя (бота).
|
||||
|
||||
Returns:
|
||||
User | None: Объект пользователя или None.
|
||||
"""
|
||||
|
||||
return self._me
|
||||
|
||||
def _resolve_notify(self, notify: Optional[bool]) -> Optional[bool]:
|
||||
|
||||
"""
|
||||
Определяет флаг уведомления.
|
||||
|
||||
Args:
|
||||
notify (Optional[bool]): Локальный флаг.
|
||||
|
||||
Returns:
|
||||
Optional[bool]: Итоговый флаг.
|
||||
"""
|
||||
|
||||
return notify if notify is not None else self.notify
|
||||
|
||||
def _resolve_parse_mode(self, mode: Optional[ParseMode]) -> Optional[ParseMode]:
|
||||
|
||||
"""
|
||||
Определяет режим форматирования.
|
||||
|
||||
Args:
|
||||
mode (Optional[ParseMode]): Локальный режим.
|
||||
|
||||
Returns:
|
||||
Optional[ParseMode]: Итоговый режим.
|
||||
"""
|
||||
|
||||
return mode if mode is not None else self.parse_mode
|
||||
|
||||
async def close_session(self) -> None:
|
||||
|
||||
"""
|
||||
Закрывает текущую сессию aiohttp.
|
||||
|
||||
Returns:
|
||||
None
|
||||
"""
|
||||
|
||||
if self.session is not None:
|
||||
await self.session.close()
|
||||
|
||||
@ -156,15 +195,17 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Отправляет сообщение в чат или пользователю.
|
||||
|
||||
:param chat_id: ID чата для отправки (обязателен, если не указан user_id)
|
||||
:param user_id: ID пользователя для отправки (обязателен, если не указан chat_id)
|
||||
:param text: Текст сообщения
|
||||
:param attachments: Список вложений к сообщению
|
||||
:param link: Данные ссылки сообщения
|
||||
:param notify: Отправлять уведомление получателю (по умолчанию берется значение из бота)
|
||||
:param parse_mode: Режим форматирования текста
|
||||
Args:
|
||||
chat_id (Optional[int]): ID чата для отправки (если не user_id).
|
||||
user_id (Optional[int]): ID пользователя (если не chat_id).
|
||||
text (Optional[str]): Текст сообщения.
|
||||
attachments (Optional[List[Attachment | InputMedia | InputMediaBuffer]]): Вложения.
|
||||
link (Optional[NewMessageLink]): Данные ссылки сообщения.
|
||||
notify (Optional[bool]): Флаг уведомления.
|
||||
parse_mode (Optional[ParseMode]): Режим форматирования текста.
|
||||
|
||||
:return: Объект отправленного сообщения
|
||||
Returns:
|
||||
Optional[SendedMessage | Error]: Отправленное сообщение или ошибка.
|
||||
"""
|
||||
|
||||
return await SendMessage(
|
||||
@ -187,10 +228,12 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Отправляет действие в чат (например, "печатает").
|
||||
|
||||
:param chat_id: ID чата для отправки действия
|
||||
:param action: Тип действия (по умолчанию SenderAction.TYPING_ON)
|
||||
Args:
|
||||
chat_id (Optional[int]): ID чата.
|
||||
action (SenderAction): Тип действия.
|
||||
|
||||
:return: Результат отправки действия
|
||||
Returns:
|
||||
SendedAction: Результат отправки действия.
|
||||
"""
|
||||
|
||||
return await SendAction(
|
||||
@ -212,14 +255,16 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Редактирует существующее сообщение.
|
||||
|
||||
:param message_id: ID сообщения для редактирования
|
||||
:param text: Новый текст сообщения
|
||||
:param attachments: Новые вложения
|
||||
:param link: Новая ссылка сообщения
|
||||
:param notify: Отправлять уведомление получателю (по умолчанию берется значение из бота)
|
||||
:param parse_mode: Режим форматирования текста
|
||||
Args:
|
||||
message_id (str): ID сообщения.
|
||||
text (Optional[str]): Новый текст.
|
||||
attachments (Optional[List[Attachment | InputMedia | InputMediaBuffer]]): Новые вложения.
|
||||
link (Optional[NewMessageLink]): Новая ссылка.
|
||||
notify (Optional[bool]): Флаг уведомления.
|
||||
parse_mode (Optional[ParseMode]): Режим форматирования текста.
|
||||
|
||||
:return: Объект отредактированного сообщения
|
||||
Returns:
|
||||
Optional[EditedMessage | Error]: Отредактированное сообщение или ошибка.
|
||||
"""
|
||||
|
||||
return await EditMessage(
|
||||
@ -240,9 +285,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Удаляет сообщение.
|
||||
|
||||
:param message_id: ID сообщения для удаления
|
||||
Args:
|
||||
message_id (str): ID сообщения.
|
||||
|
||||
:return: Результат удаления сообщения
|
||||
Returns:
|
||||
DeletedMessage: Результат удаления.
|
||||
"""
|
||||
|
||||
return await DeleteMessage(
|
||||
@ -258,9 +305,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Удаляет чат.
|
||||
|
||||
:param chat_id: ID чата для удаления
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Результат удаления чата
|
||||
Returns:
|
||||
DeletedChat: Результат удаления чата.
|
||||
"""
|
||||
|
||||
return await DeleteChat(
|
||||
@ -280,13 +329,15 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает сообщения из чата.
|
||||
|
||||
:param chat_id: ID чата (обязателен, если не указаны message_ids)
|
||||
:param message_ids: Список ID сообщений для получения
|
||||
:param from_time: Время начала периода (datetime или timestamp)
|
||||
:param to_time: Время конца периода (datetime или timestamp)
|
||||
:param count: Количество сообщений (по умолчанию 50)
|
||||
Args:
|
||||
chat_id (Optional[int]): ID чата.
|
||||
message_ids (Optional[List[str]]): ID сообщений.
|
||||
from_time (Optional[datetime | int]): Начало периода.
|
||||
to_time (Optional[datetime | int]): Конец периода.
|
||||
count (int): Количество сообщений.
|
||||
|
||||
:return: Список сообщений
|
||||
Returns:
|
||||
Messages: Список сообщений.
|
||||
"""
|
||||
|
||||
return await GetMessages(
|
||||
@ -306,9 +357,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает одно сообщение по ID.
|
||||
|
||||
:param message_id: ID сообщения
|
||||
Args:
|
||||
message_id (str): ID сообщения.
|
||||
|
||||
:return: Объект сообщения
|
||||
Returns:
|
||||
Message: Объект сообщения.
|
||||
"""
|
||||
|
||||
return await GetMessage(
|
||||
@ -319,10 +372,10 @@ class Bot(BaseConnection):
|
||||
async def get_me(self) -> User:
|
||||
|
||||
"""
|
||||
https://dev.max.ru/docs-api/methods/GET/me\n
|
||||
Получает информацию о текущем боте.
|
||||
|
||||
:return: Объект пользователя бота
|
||||
Returns:
|
||||
User: Объект пользователя бота.
|
||||
"""
|
||||
|
||||
return await GetMe(self).fetch()
|
||||
@ -335,9 +388,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает закрепленное сообщение в чате.
|
||||
|
||||
:param chat_id: ID чата
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Закрепленное сообщение
|
||||
Returns:
|
||||
GettedPin: Закрепленное сообщение.
|
||||
"""
|
||||
|
||||
return await GetPinnedMessage(
|
||||
@ -356,12 +411,14 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Изменяет информацию о боте.
|
||||
|
||||
:param name: Новое имя бота
|
||||
:param description: Новое описание бота
|
||||
:param commands: Список команд бота
|
||||
:param photo: Данные фотографии бота
|
||||
Args:
|
||||
name (Optional[str]): Новое имя бота.
|
||||
description (Optional[str]): Новое описание.
|
||||
commands (Optional[List[BotCommand]]): Команды бота.
|
||||
photo (Optional[PhotoAttachmentRequestPayload]): Фото бота.
|
||||
|
||||
:return: Обновленная информация о боте
|
||||
Returns:
|
||||
User: Обновленная информация о боте.
|
||||
"""
|
||||
|
||||
return await ChangeInfo(
|
||||
@ -381,10 +438,12 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает список чатов бота.
|
||||
|
||||
:param count: Количество чатов (по умолчанию 50)
|
||||
:param marker: Маркер для пагинации
|
||||
Args:
|
||||
count (int): Количество чатов (по умолчанию 50).
|
||||
marker (Optional[int]): Маркер для пагинации.
|
||||
|
||||
:return: Список чатов
|
||||
Returns:
|
||||
Chats: Список чатов.
|
||||
"""
|
||||
|
||||
return await GetChats(
|
||||
@ -401,9 +460,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает чат по ссылке.
|
||||
|
||||
:param link: Ссылка на чат
|
||||
Args:
|
||||
link (str): Ссылка на чат.
|
||||
|
||||
:return: Объект чата
|
||||
Returns:
|
||||
Chat: Объект чата.
|
||||
"""
|
||||
|
||||
return await GetChatByLink(bot=self, link=link).fetch()
|
||||
@ -416,9 +477,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает чат по ID.
|
||||
|
||||
:param id: ID чата
|
||||
Args:
|
||||
id (int): ID чата.
|
||||
|
||||
:return: Объект чата
|
||||
Returns:
|
||||
Chat: Объект чата.
|
||||
"""
|
||||
|
||||
return await GetChatById(bot=self, id=id).fetch()
|
||||
@ -435,13 +498,15 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Редактирует параметры чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param icon: Данные иконки чата
|
||||
:param title: Новый заголовок чата
|
||||
:param pin: ID сообщения для закрепления
|
||||
:param notify: Отправлять уведомление получателю (по умолчанию берется значение из бота)
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
icon (Optional[PhotoAttachmentRequestPayload]): Иконка.
|
||||
title (Optional[str]): Новый заголовок.
|
||||
pin (Optional[str]): ID сообщения для закрепления.
|
||||
notify (Optional[bool]): Флаг уведомления.
|
||||
|
||||
:return: Обновленный объект чата
|
||||
Returns:
|
||||
Chat: Обновленный объект чата.
|
||||
"""
|
||||
|
||||
return await EditChat(
|
||||
@ -461,9 +526,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает видео по токену.
|
||||
|
||||
:param video_token: Токен видео
|
||||
Args:
|
||||
video_token (str): Токен видео.
|
||||
|
||||
:return: Объект видео
|
||||
Returns:
|
||||
Video: Объект видео.
|
||||
"""
|
||||
|
||||
return await GetVideo(
|
||||
@ -481,11 +548,13 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Отправляет callback ответ.
|
||||
|
||||
:param callback_id: ID callback
|
||||
:param message: Сообщение для отправки
|
||||
:param notification: Текст уведомления
|
||||
Args:
|
||||
callback_id (str): ID callback.
|
||||
message (Optional[Message]): Сообщение для отправки.
|
||||
notification (Optional[str]): Текст уведомления.
|
||||
|
||||
:return: Результат отправки callback
|
||||
Returns:
|
||||
SendedCallback: Результат отправки callback.
|
||||
"""
|
||||
|
||||
return await SendCallback(
|
||||
@ -505,11 +574,13 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Закрепляет сообщение в чате.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param message_id: ID сообщения
|
||||
:param notify: Отправлять уведомление получателю (по умолчанию берется значение из бота)
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
message_id (str): ID сообщения.
|
||||
notify (Optional[bool]): Флаг уведомления.
|
||||
|
||||
:return: Закрепленное сообщение
|
||||
Returns:
|
||||
PinnedMessage: Закрепленное сообщение.
|
||||
"""
|
||||
|
||||
return await PinMessage(
|
||||
@ -527,9 +598,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Удаляет закрепленное сообщение в чате.
|
||||
|
||||
:param chat_id: ID чата
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Результат удаления
|
||||
Returns:
|
||||
DeletedPinMessage: Результат удаления.
|
||||
"""
|
||||
|
||||
return await DeletePinMessage(
|
||||
@ -543,11 +616,13 @@ class Bot(BaseConnection):
|
||||
) -> ChatMember:
|
||||
|
||||
"""
|
||||
Получает информацию о боте в конкретном чате.
|
||||
Получает информацию о боте в чате.
|
||||
|
||||
:param chat_id: ID чата
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Информация о боте в чате
|
||||
Returns:
|
||||
ChatMember: Информация о боте в чате.
|
||||
"""
|
||||
|
||||
return await GetMeFromChat(
|
||||
@ -563,9 +638,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Удаляет бота из чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Результат удаления
|
||||
Returns:
|
||||
DeletedBotFromChat: Результат удаления.
|
||||
"""
|
||||
|
||||
return await DeleteMeFromMessage(
|
||||
@ -581,9 +658,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает список администраторов чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
|
||||
:return: Список администраторов
|
||||
Returns:
|
||||
GettedListAdminChat: Список администраторов.
|
||||
"""
|
||||
|
||||
return await GetListAdminChat(
|
||||
@ -601,11 +680,13 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Добавляет администраторов в чат.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param admins: Список администраторов
|
||||
:param marker: Маркер для пагинации
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
admins (List[ChatAdmin]): Список администраторов.
|
||||
marker (Optional[int]): Маркер для пагинации.
|
||||
|
||||
:return: Результат добавления
|
||||
Returns:
|
||||
AddedListAdminChat: Результат добавления.
|
||||
"""
|
||||
|
||||
return await AddAdminChat(
|
||||
@ -624,10 +705,12 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Удаляет администратора из чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param user_id: ID пользователя
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
user_id (int): ID пользователя.
|
||||
|
||||
:return: Результат удаления
|
||||
Returns:
|
||||
RemovedAdmin: Результат удаления.
|
||||
"""
|
||||
|
||||
return await RemoveAdmin(
|
||||
@ -647,12 +730,14 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает участников чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param user_ids: Список ID участников
|
||||
:param marker: Маркер для пагинации
|
||||
:param count: Количество участников
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
user_ids (Optional[List[int]]): Список ID участников.
|
||||
marker (Optional[int]): Маркер для пагинации.
|
||||
count (Optional[int]): Количество участников.
|
||||
|
||||
:return: Список участников
|
||||
Returns:
|
||||
GettedMembersChat: Список участников.
|
||||
"""
|
||||
|
||||
return await GetMembersChat(
|
||||
@ -672,10 +757,12 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает участника чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param user_id: ID участника
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
user_id (int): ID участника.
|
||||
|
||||
:return: Участник
|
||||
Returns:
|
||||
Optional[ChatMember]: Участник.
|
||||
"""
|
||||
|
||||
members = await self.get_chat_members(
|
||||
@ -697,10 +784,12 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Добавляет участников в чат.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param user_ids: Список ID пользователей
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
user_ids (List[int]): Список ID пользователей.
|
||||
|
||||
:return: Результат добавления
|
||||
Returns:
|
||||
AddedMembersChat: Результат добавления.
|
||||
"""
|
||||
|
||||
return await AddMembersChat(
|
||||
@ -719,11 +808,13 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Исключает участника из чата.
|
||||
|
||||
:param chat_id: ID чата
|
||||
:param user_id: ID пользователя
|
||||
:param block: Блокировать пользователя (по умолчанию False)
|
||||
Args:
|
||||
chat_id (int): ID чата.
|
||||
user_id (int): ID пользователя.
|
||||
block (bool): Блокировать пользователя (по умолчанию False).
|
||||
|
||||
:return: Результат исключения
|
||||
Returns:
|
||||
RemovedMemberChat: Результат исключения.
|
||||
"""
|
||||
|
||||
return await RemoveMemberChat(
|
||||
@ -740,7 +831,8 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает обновления для бота.
|
||||
|
||||
:return: Список обновлений
|
||||
Returns:
|
||||
Dict: Список обновлений.
|
||||
"""
|
||||
|
||||
return await GetUpdates(
|
||||
@ -755,9 +847,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает URL для загрузки файлов.
|
||||
|
||||
:param type: Тип загружаемого файла
|
||||
Args:
|
||||
type (UploadType): Тип загружаемого файла.
|
||||
|
||||
:return: URL для загрузки
|
||||
Returns:
|
||||
GettedUploadUrl: URL для загрузки.
|
||||
"""
|
||||
|
||||
return await GetUploadURL(
|
||||
@ -773,9 +867,11 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Устанавливает список команд бота.
|
||||
|
||||
:param commands: Список команд
|
||||
Args:
|
||||
*commands (BotCommand): Список команд.
|
||||
|
||||
:return: Обновленная информация о боте
|
||||
Returns:
|
||||
User: Обновленная информация о боте.
|
||||
"""
|
||||
|
||||
return await ChangeInfo(
|
||||
@ -788,7 +884,8 @@ class Bot(BaseConnection):
|
||||
"""
|
||||
Получает список всех подписок.
|
||||
|
||||
:return: Объект со списком подписок
|
||||
Returns:
|
||||
GettedSubscriptions: Объект со списком подписок.
|
||||
"""
|
||||
|
||||
return await GetSubscriptions(bot=self).fetch()
|
||||
@ -802,17 +899,14 @@ class Bot(BaseConnection):
|
||||
|
||||
"""
|
||||
Подписывает бота на получение обновлений через WebHook.
|
||||
После вызова этого метода бот будет получать уведомления о новых событиях в чатах на указанный URL.
|
||||
Ваш сервер должен прослушивать один из следующих портов: `80`, `8080`, `443`, `8443`, `16384`-`32383`.
|
||||
|
||||
:param url: URL HTTP(S)-эндпойнта вашего бота. Должен начинаться с http(s)://
|
||||
:param update_types: Список типов обновлений, которые ваш бот хочет получать.
|
||||
Для полного списка типов см. объект
|
||||
:param secret: От 5 до 256 символов. Cекрет, который должен быть отправлен в заголовке X-Max-Bot-Api-Secret
|
||||
в каждом запросе Webhook. Разрешены только символы A-Z, a-z, 0-9, и дефис.
|
||||
Заголовок рекомендован, чтобы запрос поступал из установленного веб-узла
|
||||
Args:
|
||||
url (str): URL HTTP(S)-эндпойнта вашего бота.
|
||||
update_types (Optional[List[UpdateType]]): Список типов обновлений.
|
||||
secret (Optional[str]): Секрет для Webhook.
|
||||
|
||||
:return: Обновленная информация о боте
|
||||
Returns:
|
||||
Subscribed: Результат подписки.
|
||||
"""
|
||||
|
||||
return await SubscribeWebhook(
|
||||
@ -829,12 +923,12 @@ class Bot(BaseConnection):
|
||||
|
||||
"""
|
||||
Отписывает бота от получения обновлений через WebHook.
|
||||
После вызова этого метода бот перестает получать уведомления о новых событиях,
|
||||
и доступна доставка уведомлений через API с длительным опросом.
|
||||
|
||||
:param url: URL HTTP(S)-эндпойнта вашего бота. Должен начинаться с http(s)://
|
||||
Args:
|
||||
url (str): URL HTTP(S)-эндпойнта вашего бота.
|
||||
|
||||
:return: Обновленная информация о боте
|
||||
Returns:
|
||||
Unsubscribed: Результат отписки.
|
||||
"""
|
||||
|
||||
return await UnsubscribeWebhook(
|
||||
@ -845,7 +939,10 @@ class Bot(BaseConnection):
|
||||
async def delete_webhook(self):
|
||||
|
||||
"""
|
||||
Удаление всех подписок на Webhook
|
||||
Удаляет все подписки на Webhook.
|
||||
|
||||
Returns:
|
||||
None
|
||||
"""
|
||||
|
||||
subs = await self.get_subscriptions()
|
||||
@ -855,28 +952,3 @@ class Bot(BaseConnection):
|
||||
|
||||
await self.unsubscribe_webhook(sub.url)
|
||||
logger_bot.info('Удалена подписка на Webhook: %s', sub.url)
|
||||
|
||||
|
||||
# async def download_file(
|
||||
# self,
|
||||
# path: str,
|
||||
# url: str,
|
||||
# token: str
|
||||
# ):
|
||||
|
||||
# """
|
||||
# Скачивает медиа с указанной ссылки по токену, сохраняя по определенному пути
|
||||
|
||||
# :param path: Путь сохранения медиа
|
||||
# :param url: Ссылка на медиа
|
||||
# :param token: Токен медиа
|
||||
|
||||
# :return: Числовой статус
|
||||
# """
|
||||
|
||||
# return await DownloadMedia(
|
||||
# bot=self,
|
||||
# path=path,
|
||||
# media_url=url,
|
||||
# media_token=token
|
||||
# ).fetch()
|
@ -1,10 +1,27 @@
|
||||
|
||||
|
||||
from aiohttp import ClientTimeout
|
||||
|
||||
|
||||
class DefaultConnectionProperties:
|
||||
'''
|
||||
Класс для хранения параметров соединения по умолчанию для aiohttp-клиента.
|
||||
|
||||
Args:
|
||||
timeout (int): Таймаут всего соединения в секундах (по умолчанию 5 * 30).
|
||||
sock_connect (int): Таймаут установки TCP-соединения в секундах (по умолчанию 30).
|
||||
**kwargs: Дополнительные параметры, которые будут сохранены как есть.
|
||||
|
||||
Attributes:
|
||||
timeout (ClientTimeout): Экземпляр aiohttp.ClientTimeout с заданными параметрами.
|
||||
kwargs (dict): Дополнительные параметры.
|
||||
'''
|
||||
|
||||
def __init__(self, timeout: int = 5 * 30, sock_connect: int = 30, **kwargs):
|
||||
'''
|
||||
Инициализация параметров соединения.
|
||||
|
||||
Args:
|
||||
timeout (int): Таймаут всего соединения в секундах.
|
||||
sock_connect (int): Таймаут установки TCP-соединения в секундах.
|
||||
**kwargs: Дополнительные параметры.
|
||||
'''
|
||||
self.timeout = ClientTimeout(total=timeout, sock_connect=sock_connect)
|
||||
self.kwargs = kwargs
|
@ -30,9 +30,7 @@ class BaseConnection:
|
||||
"""
|
||||
Базовый класс для всех методов API.
|
||||
|
||||
Содержит общую логику выполнения запроса (например, сериализацию, отправку HTTP-запроса, обработку ответа).
|
||||
|
||||
Метод request() может быть переопределён в потомках при необходимости.
|
||||
Содержит общую логику выполнения запроса (сериализация, отправка HTTP-запроса, обработка ответа).
|
||||
"""
|
||||
|
||||
API_URL = 'https://botapi.max.ru'
|
||||
@ -41,6 +39,16 @@ class BaseConnection:
|
||||
AFTER_MEDIA_INPUT_DELAY = 2.0
|
||||
|
||||
def __init__(self) -> None:
|
||||
|
||||
"""
|
||||
Инициализация BaseConnection.
|
||||
|
||||
Атрибуты:
|
||||
bot (Optional[Bot]): Экземпляр бота.
|
||||
session (Optional[ClientSession]): aiohttp-сессия.
|
||||
after_input_media_delay (float): Задержка после ввода медиа.
|
||||
"""
|
||||
|
||||
self.bot: Optional[Bot] = None
|
||||
self.session: Optional[ClientSession] = None
|
||||
self.after_input_media_delay: float = self.AFTER_MEDIA_INPUT_DELAY
|
||||
@ -55,18 +63,22 @@ class BaseConnection:
|
||||
):
|
||||
|
||||
"""
|
||||
Выполняет HTTP-запрос к API, используя указанные параметры.
|
||||
Выполняет HTTP-запрос к API.
|
||||
|
||||
:param method: HTTP-метод запроса (GET, POST и т.д.)
|
||||
:param path: Путь к конечной точке API
|
||||
:param model: Pydantic-модель, в которую будет десериализован ответ (если is_return_raw=False)
|
||||
:param is_return_raw: Если True — вернуть "сырое" тело ответа, иначе — результат десериализации в model
|
||||
:param kwargs: Дополнительные параметры (например, query, headers, json)
|
||||
Args:
|
||||
method (HTTPMethod): HTTP-метод (GET, POST и т.д.).
|
||||
path (ApiPath | str): Путь до конечной точки.
|
||||
model (BaseModel | Any, optional): Pydantic-модель для десериализации ответа, если is_return_raw=False.
|
||||
is_return_raw (bool, optional): Если True — вернуть сырой ответ, иначе — результат десериализации.
|
||||
**kwargs: Дополнительные параметры (query, headers, json).
|
||||
|
||||
:return:
|
||||
- Объект model (если is_return_raw=False и model задан)
|
||||
Returns:
|
||||
model | dict | Error: Объект модели, dict или ошибка.
|
||||
|
||||
- dict (если is_return_raw=True)
|
||||
Raises:
|
||||
RuntimeError: Если бот не инициализирован.
|
||||
MaxConnection: Ошибка соединения.
|
||||
InvalidToken: Ошибка авторизации (401).
|
||||
"""
|
||||
|
||||
if self.bot is None:
|
||||
@ -121,14 +133,17 @@ class BaseConnection:
|
||||
path: str,
|
||||
type: UploadType
|
||||
):
|
||||
|
||||
"""
|
||||
Загружает файл на указанный URL.
|
||||
Загружает файл на сервер.
|
||||
|
||||
:param url: Конечная точка загрузки файла
|
||||
:param path: Путь к локальному файлу
|
||||
:param type: Тип файла (video, image, audio, file)
|
||||
Args:
|
||||
url (str): URL загрузки.
|
||||
path (str): Путь к файлу.
|
||||
type (UploadType): Тип файла.
|
||||
|
||||
:return: Сырой .text() ответ от сервера после загрузки файла
|
||||
Returns:
|
||||
str: Сырой .text() ответ от сервера.
|
||||
"""
|
||||
|
||||
async with aiofiles.open(path, 'rb') as f:
|
||||
@ -160,14 +175,18 @@ class BaseConnection:
|
||||
buffer: bytes,
|
||||
type: UploadType
|
||||
):
|
||||
|
||||
"""
|
||||
Загружает файл из буфера.
|
||||
|
||||
:param url: Конечная точка загрузки файла
|
||||
:param buffer: Буфер (bytes)
|
||||
:param type: Тип файла (video, image, audio, file)
|
||||
Args:
|
||||
filename (str): Имя файла.
|
||||
url (str): URL загрузки.
|
||||
buffer (bytes): Буфер данных.
|
||||
type (UploadType): Тип файла.
|
||||
|
||||
:return: Сырой .text() ответ от сервера после загрузки файла
|
||||
Returns:
|
||||
str: Сырой .text() ответ от сервера.
|
||||
"""
|
||||
|
||||
try:
|
||||
@ -198,32 +217,3 @@ class BaseConnection:
|
||||
data=form
|
||||
)
|
||||
return await response.text()
|
||||
|
||||
async def download_file(
|
||||
self,
|
||||
path: str,
|
||||
url: str,
|
||||
token: str,
|
||||
):
|
||||
"""
|
||||
Скачивает медиа с указанной ссылки по токену, сохраняя по определенному пути
|
||||
|
||||
:param path: Путь сохранения медиа
|
||||
:param url: Ссылка на медиа
|
||||
:param token: Токен медиа
|
||||
|
||||
:return: Числовой статус
|
||||
"""
|
||||
|
||||
headers = {
|
||||
'Authorization': f'Bearer {token}'
|
||||
}
|
||||
|
||||
async with ClientSession() as session:
|
||||
async with session.get(url, headers=headers) as response:
|
||||
|
||||
if response.status == 200:
|
||||
async with aiofiles.open(path, 'wb') as f:
|
||||
await f.write(await response.read())
|
||||
|
||||
return response.status
|
@ -1,4 +1,8 @@
|
||||
from typing import List
|
||||
|
||||
|
||||
class State:
|
||||
|
||||
"""
|
||||
Представляет отдельное состояние в FSM-группе.
|
||||
|
||||
@ -16,6 +20,7 @@ class State:
|
||||
|
||||
|
||||
class StatesGroup:
|
||||
|
||||
"""
|
||||
Базовый класс для описания группы состояний FSM.
|
||||
|
||||
@ -23,7 +28,8 @@ class StatesGroup:
|
||||
"""
|
||||
|
||||
@classmethod
|
||||
def states(cls) -> list[str]:
|
||||
def states(cls) -> List[str]:
|
||||
|
||||
"""
|
||||
Получить список всех состояний в формате 'ИмяКласса:имя_состояния'.
|
||||
|
||||
|
@ -8,6 +8,8 @@ from asyncio.exceptions import TimeoutError as AsyncioTimeoutError
|
||||
|
||||
from aiohttp import ClientConnectorError
|
||||
|
||||
from maxapi.exceptions.dispatcher import HandlerException
|
||||
|
||||
from .filters.filter import BaseFilter
|
||||
from .filters.middleware import BaseMiddleware
|
||||
from .filters.handler import Handler
|
||||
@ -61,8 +63,8 @@ class Dispatcher:
|
||||
"""
|
||||
Инициализация диспетчера.
|
||||
|
||||
:param router_id: Идентификатор роутера, используется при логгировании.
|
||||
По умолчанию индекс зарегистированного роутера в списке
|
||||
Args:
|
||||
router_id (str | None): Идентификатор роутера для логов.
|
||||
"""
|
||||
|
||||
self.router_id = router_id
|
||||
@ -132,6 +134,17 @@ class Dispatcher:
|
||||
handler: Callable[[Any, dict[str, Any]], Awaitable[Any]]
|
||||
) -> Callable[[Any, dict[str, Any]], Awaitable[Any]]:
|
||||
|
||||
"""
|
||||
Формирует цепочку вызова middleware вокруг хендлера.
|
||||
|
||||
Args:
|
||||
middlewares (list[BaseMiddleware]): Список middleware.
|
||||
handler (Callable): Финальный обработчик.
|
||||
|
||||
Returns:
|
||||
Callable: Обёрнутый обработчик.
|
||||
"""
|
||||
|
||||
for mw in reversed(middlewares):
|
||||
handler = functools.partial(mw, handler)
|
||||
|
||||
@ -142,7 +155,8 @@ class Dispatcher:
|
||||
"""
|
||||
Добавляет указанные роутеры в диспетчер.
|
||||
|
||||
:param routers: Роутеры для добавления.
|
||||
Args:
|
||||
*routers (Router): Роутеры для добавления.
|
||||
"""
|
||||
|
||||
self.routers += [r for r in routers]
|
||||
@ -150,9 +164,10 @@ class Dispatcher:
|
||||
def outer_middleware(self, middleware: BaseMiddleware) -> None:
|
||||
|
||||
"""
|
||||
Добавляет Middleware на первое место в списке
|
||||
Добавляет Middleware на первое место в списке.
|
||||
|
||||
:param: middleware: Middleware
|
||||
Args:
|
||||
middleware (BaseMiddleware): Middleware.
|
||||
"""
|
||||
|
||||
self.middlewares.insert(0, middleware)
|
||||
@ -160,9 +175,10 @@ class Dispatcher:
|
||||
def middleware(self, middleware: BaseMiddleware) -> None:
|
||||
|
||||
"""
|
||||
Добавляет Middleware в список
|
||||
Добавляет Middleware в конец списка.
|
||||
|
||||
:param middleware: Middleware
|
||||
Args:
|
||||
middleware (BaseMiddleware): Middleware.
|
||||
"""
|
||||
|
||||
self.middlewares.append(middleware)
|
||||
@ -170,9 +186,10 @@ class Dispatcher:
|
||||
def filter(self, base_filter: BaseFilter) -> None:
|
||||
|
||||
"""
|
||||
Добавляет фильтр в список
|
||||
Добавляет фильтр в список.
|
||||
|
||||
:param base_filter: Фильтр
|
||||
Args:
|
||||
base_filter (BaseFilter): Фильтр.
|
||||
"""
|
||||
|
||||
self.base_filters.append(base_filter)
|
||||
@ -182,7 +199,8 @@ class Dispatcher:
|
||||
"""
|
||||
Подготавливает диспетчер: сохраняет бота, регистрирует обработчики, вызывает on_started.
|
||||
|
||||
:param bot: Экземпляр бота.
|
||||
Args:
|
||||
bot (Bot): Экземпляр бота.
|
||||
"""
|
||||
|
||||
self.bot = bot
|
||||
@ -208,11 +226,14 @@ class Dispatcher:
|
||||
def __get_memory_context(self, chat_id: int, user_id: int):
|
||||
|
||||
"""
|
||||
Возвращает существующий или создает новый контекст по chat_id и user_id.
|
||||
Возвращает существующий или создаёт новый MemoryContext по chat_id и user_id.
|
||||
|
||||
:param chat_id: Идентификатор чата.
|
||||
:param user_id: Идентификатор пользователя.
|
||||
:return: Объект MemoryContext.
|
||||
Args:
|
||||
chat_id (int): Идентификатор чата.
|
||||
user_id (int): Идентификатор пользователя.
|
||||
|
||||
Returns:
|
||||
MemoryContext: Контекст.
|
||||
"""
|
||||
|
||||
for ctx in self.contexts:
|
||||
@ -223,10 +244,23 @@ class Dispatcher:
|
||||
self.contexts.append(new_ctx)
|
||||
return new_ctx
|
||||
|
||||
async def call_handler(self, handler, event_object, data):
|
||||
async def call_handler(
|
||||
self,
|
||||
handler: Callable[[Any, dict[str, Any]], Awaitable[Any]],
|
||||
event_object: UpdateType,
|
||||
data: Dict[str, Any]
|
||||
):
|
||||
|
||||
"""
|
||||
Правка аргументов конечной функции хендлера и ее вызов
|
||||
Вызывает хендлер с нужными аргументами.
|
||||
|
||||
Args:
|
||||
handler: Handler.
|
||||
event_object: Объект события.
|
||||
data: Данные для хендлера.
|
||||
|
||||
Returns:
|
||||
None
|
||||
"""
|
||||
|
||||
func_args = handler.func_event.__annotations__.keys()
|
||||
@ -243,6 +277,17 @@ class Dispatcher:
|
||||
filters: List[BaseFilter]
|
||||
) -> Optional[Dict[str, Any]] | Literal[False]:
|
||||
|
||||
"""
|
||||
Асинхронно применяет фильтры к событию.
|
||||
|
||||
Args:
|
||||
event (UpdateUnion): Событие.
|
||||
filters (List[BaseFilter]): Список фильтров.
|
||||
|
||||
Returns:
|
||||
Optional[Dict[str, Any]] | Literal[False]: Словарь с результатом или False.
|
||||
"""
|
||||
|
||||
data = {}
|
||||
|
||||
for _filter in filters:
|
||||
@ -259,9 +304,10 @@ class Dispatcher:
|
||||
async def handle(self, event_object: UpdateUnion):
|
||||
|
||||
"""
|
||||
Основной обработчик события. Применяет фильтры, middleware и вызывает подходящий handler.
|
||||
Основной обработчик события. Применяет фильтры, middleware и вызывает нужный handler.
|
||||
|
||||
:param event_object: Событие, пришедшее в бот.
|
||||
Args:
|
||||
event_object (UpdateUnion): Событие.
|
||||
"""
|
||||
|
||||
try:
|
||||
@ -336,25 +382,35 @@ class Dispatcher:
|
||||
|
||||
kwargs_filtered = {k: v for k, v in kwargs.items() if k in func_args}
|
||||
|
||||
try:
|
||||
await handler_chain(event_object, kwargs_filtered)
|
||||
except:
|
||||
raise HandlerException(
|
||||
handler_title=handler.func_event.__name__,
|
||||
memory_context={
|
||||
'data': await memory_context.get_data(),
|
||||
'state': current_state
|
||||
}
|
||||
)
|
||||
|
||||
logger_dp.info(f'Обработано: {router_id} | {process_info}')
|
||||
logger_dp.info(f'Обработано: router_id: {router_id} | {process_info}')
|
||||
|
||||
is_handled = True
|
||||
break
|
||||
|
||||
if not is_handled:
|
||||
logger_dp.info(f'Проигнорировано: {router_id} | {process_info}')
|
||||
logger_dp.info(f'Проигнорировано: router_id: {router_id} | {process_info}')
|
||||
|
||||
except Exception as e:
|
||||
logger_dp.error(f"Ошибка при обработке события: {router_id} | {process_info} | {e} ")
|
||||
logger_dp.error(f"Ошибка при обработке события: router_id: {router_id} | {process_info} | {e} ")
|
||||
|
||||
async def start_polling(self, bot: Bot):
|
||||
|
||||
"""
|
||||
Запускает цикл получения обновлений с сервера (long polling).
|
||||
Запускает цикл получения обновлений (long polling).
|
||||
|
||||
:param bot: Экземпляр бота.
|
||||
Args:
|
||||
bot (Bot): Экземпляр бота.
|
||||
"""
|
||||
|
||||
self.polling = True
|
||||
@ -399,9 +455,10 @@ class Dispatcher:
|
||||
"""
|
||||
Запускает FastAPI-приложение для приёма обновлений через вебхук.
|
||||
|
||||
:param bot: Экземпляр бота.
|
||||
:param host: Хост, на котором запускается сервер.
|
||||
:param port: Порт сервера.
|
||||
Args:
|
||||
bot (Bot): Экземпляр бота.
|
||||
host (str): Хост сервера.
|
||||
port (int): Порт сервера.
|
||||
"""
|
||||
|
||||
if not FASTAPI_INSTALLED:
|
||||
@ -422,19 +479,6 @@ class Dispatcher:
|
||||
'\n\t pip install maxapi[webhook]'
|
||||
)
|
||||
|
||||
# try:
|
||||
# from fastapi import Request
|
||||
# from fastapi.responses import JSONResponse
|
||||
# except ImportError:
|
||||
# raise ImportError(
|
||||
# '\n\t Не установлен fastapi!'
|
||||
# '\n\t Выполните команду для установки fastapi: '
|
||||
# '\n\t pip install fastapi>=0.68.0'
|
||||
# '\n\t Или сразу все зависимости для работы вебхука:'
|
||||
# '\n\t pip install maxapi[webhook]'
|
||||
# )
|
||||
|
||||
|
||||
@self.webhook_post('/')
|
||||
async def _(request: Request):
|
||||
event_json = await request.json()
|
||||
@ -457,24 +501,14 @@ class Dispatcher:
|
||||
async def init_serve(self, bot: Bot, host: str = 'localhost', port: int = 8080, **kwargs):
|
||||
|
||||
"""
|
||||
Запускает сервер для обработки входящих вебхуков.
|
||||
Запускает сервер для обработки вебхуков.
|
||||
|
||||
:param bot: Экземпляр бота.
|
||||
:param host: Хост, на котором запускается сервер.
|
||||
:param port: Порт сервера.
|
||||
Args:
|
||||
bot (Bot): Экземпляр бота.
|
||||
host (str): Хост.
|
||||
port (int): Порт.
|
||||
"""
|
||||
|
||||
# try:
|
||||
# from uvicorn import Config, Server
|
||||
# except ImportError:
|
||||
# raise ImportError(
|
||||
# '\n\t Не установлен uvicorn!'
|
||||
# '\n\t Выполните команду для установки uvicorn: '
|
||||
# '\n\t pip install uvicorn>=0.15.0'
|
||||
# '\n\t Или сразу все зависимости для работы вебхука:'
|
||||
# '\n\t pip install maxapi[webhook]'
|
||||
# )
|
||||
|
||||
if not UVICORN_INSTALLED:
|
||||
raise ImportError(
|
||||
'\n\t Не установлен uvicorn!'
|
||||
@ -504,10 +538,10 @@ class Router(Dispatcher):
|
||||
def __init__(self, router_id: str | None = None):
|
||||
|
||||
"""
|
||||
Инициализация диспетчера.
|
||||
Инициализация роутера.
|
||||
|
||||
:param router_id: Идентификатор роутера, используется при логгировании.
|
||||
По умолчанию индекс зарегистированного роутера в списке
|
||||
Args:
|
||||
router_id (str | None): Идентификатор роутера для логов.
|
||||
"""
|
||||
|
||||
super().__init__(router_id)
|
||||
@ -524,8 +558,9 @@ class Event:
|
||||
"""
|
||||
Инициализирует событие-декоратор.
|
||||
|
||||
:param update_type: Тип события (UpdateType).
|
||||
:param router: Роутер или диспетчер, в который регистрируется обработчик.
|
||||
Args:
|
||||
update_type (UpdateType): Тип события.
|
||||
router (Dispatcher | Router): Экземпляр роутера или диспетчера.
|
||||
"""
|
||||
|
||||
self.update_type = update_type
|
||||
@ -536,7 +571,8 @@ class Event:
|
||||
"""
|
||||
Регистрирует функцию как обработчик события.
|
||||
|
||||
:return: Исходная функция.
|
||||
Returns:
|
||||
Callable: Исходная функция.
|
||||
"""
|
||||
|
||||
def decorator(func_event: Callable):
|
||||
|
@ -9,13 +9,18 @@ __all__ = [
|
||||
|
||||
|
||||
def filter_attrs(obj: object, *filters: MagicFilter) -> bool:
|
||||
|
||||
"""
|
||||
Применяет один или несколько фильтров MagicFilter к объекту.
|
||||
|
||||
:param obj: Любой объект с атрибутами (например, event/message)
|
||||
:param filters: Один или несколько MagicFilter выражений
|
||||
:return: True, если все фильтры возвращают True, иначе False
|
||||
Args:
|
||||
obj (object): Объект, к которому применяются фильтры (например, event или message).
|
||||
*filters (MagicFilter): Один или несколько выражений MagicFilter.
|
||||
|
||||
Returns:
|
||||
bool: True, если все фильтры возвращают True, иначе False.
|
||||
"""
|
||||
|
||||
try:
|
||||
return all(f.resolve(obj) for f in filters)
|
||||
except Exception:
|
||||
|
@ -12,12 +12,12 @@ class Command(BaseFilter):
|
||||
Фильтр сообщений на соответствие команде.
|
||||
|
||||
Args:
|
||||
commands (str | list[str]): Ожидаемая команда или список команд без префикса.
|
||||
commands (str | List[str]): Ожидаемая команда или список команд без префикса.
|
||||
prefix (str, optional): Префикс команды (по умолчанию '/').
|
||||
check_case (bool, optional): Учитывать регистр при сравнении (по умолчанию False).
|
||||
|
||||
Attributes:
|
||||
commands (list[str]): Список команд без префикса.
|
||||
commands (List[str]): Список команд без префикса.
|
||||
prefix (str): Префикс команды.
|
||||
check_case (bool): Флаг чувствительности к регистру.
|
||||
"""
|
||||
|
@ -6,5 +6,16 @@ if TYPE_CHECKING:
|
||||
|
||||
|
||||
class BaseFilter:
|
||||
|
||||
"""
|
||||
Базовый класс для фильтров.
|
||||
|
||||
Определяет интерфейс фильтрации событий.
|
||||
Потомки должны переопределять метод __call__.
|
||||
|
||||
Methods:
|
||||
__call__(event): Асинхронная проверка события на соответствие фильтру.
|
||||
"""
|
||||
|
||||
async def __call__(self, event: UpdateUnion) -> bool | dict:
|
||||
return True
|
@ -17,7 +17,7 @@ class Handler:
|
||||
"""
|
||||
Обработчик события.
|
||||
|
||||
Позволяет связать функцию-обработчик с типом обновления, состоянием и набором фильтров.
|
||||
Связывает функцию-обработчик с типом события, состояниями и фильтрами.
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
@ -29,15 +29,12 @@ class Handler:
|
||||
):
|
||||
|
||||
"""
|
||||
Инициализация обработчика.
|
||||
Создаёт обработчик события.
|
||||
|
||||
:param args: Список фильтров и состояний, в том числе:
|
||||
- MagicFilter — фильтр события,
|
||||
- State — состояние FSM,
|
||||
- Command — команда для фильтрации по началу текста сообщения.
|
||||
:param func_event: Функция-обработчик события
|
||||
:param update_type: Тип обновления (события), на которое подписан обработчик
|
||||
:param kwargs: Дополнительные параметры (не используются)
|
||||
Args:
|
||||
*args: Список фильтров (MagicFilter, State, Command, BaseFilter, BaseMiddleware).
|
||||
func_event (Callable): Функция-обработчик.
|
||||
update_type (UpdateType): Тип обновления.
|
||||
"""
|
||||
|
||||
self.func_event: Callable = func_event
|
||||
@ -57,5 +54,6 @@ class Handler:
|
||||
elif isinstance(arg, BaseFilter):
|
||||
self.base_filters.append(arg)
|
||||
else:
|
||||
logger_dp.info(f'Обнаружен неизвестный фильтр `{arg}` при '
|
||||
f'регистрации функции `{func_event.__name__}`')
|
||||
logger_dp.info(
|
||||
f'Неизвестный фильтр `{arg}` при регистрации `{func_event.__name__}`'
|
||||
)
|
||||
|
@ -1,10 +1,30 @@
|
||||
from typing import Any, Callable, Awaitable
|
||||
|
||||
class BaseMiddleware:
|
||||
|
||||
"""
|
||||
Базовый класс для мидлварей.
|
||||
|
||||
Используется для обработки события до и после вызова хендлера.
|
||||
"""
|
||||
|
||||
async def __call__(
|
||||
self,
|
||||
handler: Callable[[Any, dict[str, Any]], Awaitable[Any]],
|
||||
event_object: Any,
|
||||
data: dict[str, Any]
|
||||
) -> Any:
|
||||
|
||||
"""
|
||||
Вызывает хендлер с переданным событием и данными.
|
||||
|
||||
Args:
|
||||
handler (Callable): Хендлер события.
|
||||
event_object (Any): Событие.
|
||||
data (dict): Дополнительные данные.
|
||||
|
||||
Returns:
|
||||
Any: Результат работы хендлера.
|
||||
"""
|
||||
|
||||
return await handler(event_object, data)
|
@ -114,29 +114,3 @@ class Attachment(BaseModel):
|
||||
|
||||
class Config:
|
||||
use_enum_values = True
|
||||
|
||||
# async def download(
|
||||
# self,
|
||||
# path: str
|
||||
# ):
|
||||
|
||||
# """
|
||||
# Скачивает медиа, сохраняя по определенному пути
|
||||
|
||||
# :param path: Путь сохранения медиа
|
||||
|
||||
# :return: Числовой статус
|
||||
# """
|
||||
|
||||
# if not hasattr(self.payload, 'token') or \
|
||||
# not hasattr(self.payload, 'url'):
|
||||
# raise NotAvailableForDownload()
|
||||
|
||||
# elif not self.payload.token or not self.payload.url:
|
||||
# raise NotAvailableForDownload(f'Медиа типа `{self.type}` недоступно для скачивания')
|
||||
|
||||
# return await self.bot.download_file(
|
||||
# path=path,
|
||||
# url=self.payload.url,
|
||||
# token=self.payload.token,
|
||||
# )
|
@ -11,7 +11,6 @@ class Audio(Attachment):
|
||||
Вложение с типом аудио.
|
||||
|
||||
Attributes:
|
||||
type (Literal['audio']): Тип вложения, всегда 'audio'.
|
||||
transcription (Optional[str]): Транскрипция аудио (если есть).
|
||||
"""
|
||||
|
||||
|
@ -5,7 +5,8 @@ from .button import Button
|
||||
|
||||
class RequestGeoLocationButton(Button):
|
||||
|
||||
"""Кнопка запроса геолокации пользователя.
|
||||
"""
|
||||
Кнопка запроса геолокации пользователя.
|
||||
|
||||
Attributes:
|
||||
quick: Если True, запрашивает геолокацию без дополнительного
|
||||
|
@ -8,9 +8,6 @@ class Contact(Attachment):
|
||||
|
||||
"""
|
||||
Вложение с типом контакта.
|
||||
|
||||
Attributes:
|
||||
type (Literal['contact']): Тип вложения, всегда 'contact'.
|
||||
"""
|
||||
|
||||
type: Literal[AttachmentType.CONTACT]
|
@ -11,7 +11,6 @@ class File(Attachment):
|
||||
Вложение с типом файла.
|
||||
|
||||
Attributes:
|
||||
type (Literal['file']): Тип вложения, всегда 'file'.
|
||||
filename (Optional[str]): Имя файла.
|
||||
size (Optional[int]): Размер файла в байтах.
|
||||
"""
|
||||
|
@ -11,7 +11,6 @@ class Location(Attachment):
|
||||
Вложение с типом геолокации.
|
||||
|
||||
Attributes:
|
||||
type (Literal['location']): Тип вложения, всегда 'location'.
|
||||
latitude (Optional[float]): Широта.
|
||||
longitude (Optional[float]): Долгота.
|
||||
"""
|
||||
|
@ -11,7 +11,6 @@ class Share(Attachment):
|
||||
Вложение с типом "share" (поделиться).
|
||||
|
||||
Attributes:
|
||||
type (Literal['share']): Тип вложения, всегда 'share'.
|
||||
title (Optional[str]): Заголовок для шаринга.
|
||||
description (Optional[str]): Описание.
|
||||
image_url (Optional[str]): URL изображения для предпросмотра.
|
||||
|
@ -11,7 +11,6 @@ class Sticker(Attachment):
|
||||
Вложение с типом стикера.
|
||||
|
||||
Attributes:
|
||||
type (Literal['sticker']): Тип вложения, всегда 'sticker'.
|
||||
width (Optional[int]): Ширина стикера в пикселях.
|
||||
height (Optional[int]): Высота стикера в пикселях.
|
||||
"""
|
||||
|
@ -51,7 +51,6 @@ class Video(Attachment):
|
||||
Вложение с типом видео.
|
||||
|
||||
Attributes:
|
||||
type (Optional[Literal['video']]): Тип вложения, всегда 'video'.
|
||||
token (Optional[str]): Токен видео.
|
||||
urls (Optional[VideoUrl]): URLs видео разных разрешений.
|
||||
thumbnail (VideoThumbnail): Миниатюра видео.
|
||||
|
@ -6,6 +6,7 @@ from ..enums.upload_type import UploadType
|
||||
|
||||
|
||||
class InputMedia:
|
||||
|
||||
"""
|
||||
Класс для представления медиафайла.
|
||||
|
||||
@ -15,16 +16,19 @@ class InputMedia:
|
||||
"""
|
||||
|
||||
def __init__(self, path: str):
|
||||
|
||||
"""
|
||||
Инициализирует объект медиафайла.
|
||||
|
||||
Args:
|
||||
path (str): Путь к файлу.
|
||||
"""
|
||||
|
||||
self.path = path
|
||||
self.type = self.__detect_file_type(path)
|
||||
|
||||
def __detect_file_type(self, path: str) -> UploadType:
|
||||
|
||||
"""
|
||||
Определяет тип файла на основе его содержимого (MIME-типа).
|
||||
|
||||
@ -34,6 +38,7 @@ class InputMedia:
|
||||
Returns:
|
||||
UploadType: Тип файла (VIDEO, IMAGE, AUDIO или FILE).
|
||||
"""
|
||||
|
||||
with open(path, 'rb') as f:
|
||||
sample = f.read(4096)
|
||||
|
||||
@ -60,6 +65,7 @@ class InputMedia:
|
||||
|
||||
|
||||
class InputMediaBuffer:
|
||||
|
||||
"""
|
||||
Класс для представления медиафайла из буфера.
|
||||
|
||||
@ -69,6 +75,7 @@ class InputMediaBuffer:
|
||||
"""
|
||||
|
||||
def __init__(self, buffer: bytes, filename: str | None = None):
|
||||
|
||||
"""
|
||||
Инициализирует объект медиафайла из буфера.
|
||||
|
||||
@ -76,6 +83,7 @@ class InputMediaBuffer:
|
||||
buffer (IO): Буфер с содержимым файла.
|
||||
filename (str): Название файла (по умолчанию присваивается uuid4).
|
||||
"""
|
||||
|
||||
self.filename = filename
|
||||
self.buffer = buffer
|
||||
self.type = self.__detect_file_type(buffer)
|
||||
|
@ -6,6 +6,17 @@ from .update import Update
|
||||
|
||||
|
||||
class MessageChatCreated(Update):
|
||||
|
||||
"""
|
||||
Событие создания чата.
|
||||
|
||||
Attributes:
|
||||
chat (Chat): Объект чата.
|
||||
title (Optional[str]): Название чата.
|
||||
message_id (Optional[str]): ID сообщения.
|
||||
start_payload (Optional[str]): Payload для старта.
|
||||
"""
|
||||
|
||||
chat: Chat
|
||||
title: Optional[str] = None
|
||||
message_id: Optional[str] = None
|
||||
|
@ -5,7 +5,8 @@ from ..types.attachments.attachment import Attachment, ButtonsPayload
|
||||
|
||||
class InlineKeyboardBuilder:
|
||||
|
||||
"""Конструктор инлайн-клавиатур.
|
||||
"""
|
||||
Конструктор инлайн-клавиатур.
|
||||
|
||||
Позволяет удобно собирать кнопки в ряды и формировать из них клавиатуру
|
||||
для отправки в сообщениях.
|
||||
@ -16,7 +17,8 @@ class InlineKeyboardBuilder:
|
||||
|
||||
def row(self, *buttons: InlineButtonUnion):
|
||||
|
||||
"""Добавить новый ряд кнопок в клавиатуру.
|
||||
"""
|
||||
Добавить новый ряд кнопок в клавиатуру.
|
||||
|
||||
Args:
|
||||
*buttons: Произвольное количество кнопок для добавления в ряд.
|
||||
@ -26,7 +28,8 @@ class InlineKeyboardBuilder:
|
||||
|
||||
def add(self, button: InlineButtonUnion):
|
||||
|
||||
"""Добавить кнопку в последний ряд клавиатуры.
|
||||
"""
|
||||
Добавить кнопку в последний ряд клавиатуры.
|
||||
|
||||
Args:
|
||||
button: Кнопка для добавления.
|
||||
@ -36,7 +39,8 @@ class InlineKeyboardBuilder:
|
||||
|
||||
def as_markup(self):
|
||||
|
||||
"""Собрать клавиатуру в объект для отправки.
|
||||
"""
|
||||
Собрать клавиатуру в объект для отправки.
|
||||
|
||||
Returns:
|
||||
Объект вложения с типом INLINE_KEYBOARD.
|
||||
|
@ -22,8 +22,19 @@ if TYPE_CHECKING:
|
||||
from ..bot import Bot
|
||||
|
||||
|
||||
|
||||
async def enrich_event(event_object: Any, bot: Bot) -> Any:
|
||||
|
||||
"""
|
||||
Дополняет объект события данными чата, пользователя и ссылкой на бота.
|
||||
|
||||
Args:
|
||||
event_object (Any): Событие, которое нужно дополнить.
|
||||
bot (Bot): Экземпляр бота.
|
||||
|
||||
Returns:
|
||||
Any: Обновлённый объект события.
|
||||
"""
|
||||
|
||||
if not bot.auto_requests:
|
||||
return event_object
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user