From 1374d863f04d03a73b751ec3a98e7f70a69e8a2b Mon Sep 17 00:00:00 2001 From: Denis Date: Fri, 20 Jun 2025 02:24:14 +0300 Subject: [PATCH] =?UTF-8?q?=D0=94=D0=BE=D0=B1=D0=B0=D0=B2=D0=BB=D0=B5?= =?UTF-8?q?=D0=BD=20types.InputMedia=20=D0=B4=D0=BB=D1=8F=20=D0=BF=D1=80?= =?UTF-8?q?=D0=BE=D1=81=D1=82=D0=BE=D0=B9=20=D0=B7=D0=B0=D0=B3=D1=80=D1=83?= =?UTF-8?q?=D0=B7=D0=BA=D0=B8=20=D0=BC=D0=B5=D0=B4=D0=B8=D0=B0=D1=84=D0=B0?= =?UTF-8?q?=D0=B9=D0=BB=D0=BE=D0=B2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- example.py | 151 ------------------- example/audio.mp3 | Bin 0 -> 52079 bytes example/example.py | 85 +++++++---- example/for_example.py | 18 ++- for_example.py | 10 -- maxapi/bot.py | 13 +- maxapi/connection/base.py | 62 ++++++-- maxapi/dispatcher.py | 5 +- maxapi/enums/api_path.py | 3 +- maxapi/enums/chat_status.py | 9 ++ maxapi/enums/upload_type.py | 8 + maxapi/filters/handler.py | 2 +- maxapi/loggers.py | 1 + maxapi/methods/add_admin_chat.py | 3 - maxapi/methods/add_members_chat.py | 3 - maxapi/methods/change_info.py | 2 - maxapi/methods/get_chat_by_id.py | 5 - maxapi/methods/get_chat_by_link.py | 4 - maxapi/methods/get_chats.py | 2 - maxapi/methods/get_list_admin_chat.py | 3 - maxapi/methods/get_me_from_chat.py | 4 +- maxapi/methods/get_members_chat.py | 3 - maxapi/methods/get_upload_url.py | 35 +++++ maxapi/methods/send_message.py | 86 +++++++++-- maxapi/methods/types/getted_upload_url.py | 9 ++ maxapi/methods/types/upload_file_response.py | 5 + maxapi/types/__init__.py | 3 + maxapi/types/attachments/attachment.py | 3 + maxapi/types/attachments/upload.py | 14 ++ maxapi/types/callback.py | 4 +- maxapi/types/chats.py | 13 +- maxapi/types/errors.py | 2 +- maxapi/types/input_media.py | 24 +++ 33 files changed, 332 insertions(+), 262 deletions(-) delete mode 100644 example.py create mode 100644 example/audio.mp3 delete mode 100644 for_example.py create mode 100644 maxapi/enums/chat_status.py create mode 100644 maxapi/enums/upload_type.py create mode 100644 maxapi/methods/get_upload_url.py create mode 100644 maxapi/methods/types/getted_upload_url.py create mode 100644 maxapi/methods/types/upload_file_response.py create mode 100644 maxapi/types/attachments/upload.py create mode 100644 maxapi/types/input_media.py diff --git a/example.py b/example.py deleted file mode 100644 index 213f65d..0000000 --- a/example.py +++ /dev/null @@ -1,151 +0,0 @@ -import asyncio -import logging - -from maxapi import Bot, Dispatcher, F -from maxapi.context import MemoryContext, State, StatesGroup -from maxapi.types import Command, MessageCreated, CallbackButton, MessageCallback, BotCommand -from maxapi.utils.inline_keyboard import InlineKeyboardBuilder - -from for_example import router - -logging.basicConfig(level=logging.INFO) - -bot = Bot('f9LHodD0cOL5NY7All_9xJRh5ZhPw6bRvq_0Adm8-1bZZEHdRy6_ZHDMNVPejUYNZg7Zhty-wKHNv2X2WJBQ') -dp = Dispatcher() -dp.include_routers(router) - - -start_text = '''Пример чат-бота для MAX 💙 - -Мои команды: - -/clear очищает ваш контекст -/state или /context показывают ваше контекстное состояние -/data показывает вашу контекстную память -''' - - -class Form(StatesGroup): - name = State() - age = State() - - -@dp.on_started() -async def _(): - logging.info('Бот стартовал!') - - -@dp.message_created(Command('clear')) -async def hello(event: MessageCreated, context: MemoryContext): - await context.clear() - await event.message.answer(f"Ваш контекст был очищен!") - - -@dp.message_created(Command('data')) -async def hello(event: MessageCreated, context: MemoryContext): - data = await context.get_data() - await event.message.answer(f"Ваша контекстная память: {str(data)}") - - -@dp.message_created(Command('context')) -@dp.message_created(Command('state')) -async def hello(event: MessageCreated, context: MemoryContext): - data = await context.get_state() - await event.message.answer(f"Ваше контекстное состояние: {str(data)}") - - -@dp.message_created(Command('start')) -async def hello(event: MessageCreated): - builder = InlineKeyboardBuilder() - - builder.row( - CallbackButton( - text='Ввести свое имя', - payload='btn_1' - ), - CallbackButton( - text='Ввести свой возраст', - payload='btn_2' - ) - ) - builder.row( - CallbackButton( - text='Не хочу', - payload='btn_3' - ) - ) - - await event.message.answer( - text=start_text, - attachments=[builder.as_markup()] # Для MAX клавиатура это вложение, - ) # поэтому она в списке вложений - - -@dp.message_callback(F.callback.payload == 'btn_1') -async def hello(event: MessageCallback, context: MemoryContext): - await context.set_state(Form.name) - await event.message.delete() - await event.message.answer(f'Отправьте свое имя:') - - -@dp.message_callback(F.callback.payload == 'btn_2') -async def hello(event: MessageCallback, context: MemoryContext): - await context.set_state(Form.age) - await event.message.delete() - await event.message.answer(f'Отправьте ваш возраст:') - - -@dp.message_callback(F.callback.payload == 'btn_3') -async def hello(event: MessageCallback, context: MemoryContext): - await event.message.delete() - await event.message.answer(f'Ну ладно 🥲') - - -@dp.message_created(F.message.body.text, Form.name) -async def hello(event: MessageCreated, context: MemoryContext): - await context.update_data(name=event.message.body.text) - - data = await context.get_data() - - await event.message.answer(f"Приятно познакомиться, {data['name'].title()}!") - - -@dp.message_created(F.message.body.text, Form.age) -async def hello(event: MessageCreated, context: MemoryContext): - await context.update_data(age=event.message.body.text) - - await event.message.answer(f"Ого! А мне всего пару недель 😁") - - -async def main(): - await bot.set_my_commands( - BotCommand( - name='/start', - description='Перезапустить бота' - ), - BotCommand( - name='/clear', - description='Очищает ваш контекст' - ), - BotCommand( - name='/state', - description='Показывают ваше контекстное состояние' - ), - BotCommand( - name='/data', - description='Показывает вашу контекстную память' - ), - BotCommand( - name='/context', - description='Показывают ваше контекстное состояние' - ) - ) - await dp.start_polling(bot) - # await dp.handle_webhook( - # bot=bot, - # host='localhost', - # port=8080 - # ) - - -asyncio.run(main()) \ No newline at end of file diff --git a/example/audio.mp3 b/example/audio.mp3 new file mode 100644 index 0000000000000000000000000000000000000000..23c2e3aaa31e160505bc427651b25807cc69262f GIT binary patch literal 52079 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 GettedUploadUrl: + params = self.bot.params.copy() + + params['type'] = self.type.value + + return await super().request( + method=HTTPMethod.POST, + path=ApiPath.UPLOADS, + model=GettedUploadUrl, + params=params, + ) \ No newline at end of file diff --git a/maxapi/methods/send_message.py b/maxapi/methods/send_message.py index 65b2a23..1716e2a 100644 --- a/maxapi/methods/send_message.py +++ b/maxapi/methods/send_message.py @@ -1,20 +1,33 @@ +import asyncio from typing import List, TYPE_CHECKING +from json import loads as json_loads + +from ..enums.upload_type import UploadType + +from ..types.attachments.upload import AttachmentPayload, AttachmentUpload +from ..types.errors import Error from .types.sended_message import SendedMessage from ..types.message import NewMessageLink +from ..types.input_media import InputMedia from ..types.attachments.attachment import Attachment from ..enums.parse_mode import ParseMode from ..enums.http_method import HTTPMethod from ..enums.api_path import ApiPath from ..connection.base import BaseConnection +from ..loggers import logger_bot if TYPE_CHECKING: from ..bot import Bot +class UploadResponse: + token: str = None + + class SendMessage(BaseConnection): def __init__( self, @@ -23,7 +36,7 @@ class SendMessage(BaseConnection): user_id: int = None, disable_link_preview: bool = False, text: str = None, - attachments: List[Attachment] = None, + attachments: List[Attachment | InputMedia] = None, link: NewMessageLink = None, notify: bool = True, parse_mode: ParseMode = None @@ -38,10 +51,41 @@ class SendMessage(BaseConnection): self.notify = notify self.parse_mode = parse_mode + async def __process_input_media( + self, + att: InputMedia + ): + upload = await self.bot.get_upload_url(att.type) + + upload_file_response = await self.upload_file( + url=upload.url, + path=att.path, + type=att.type + ) + + if att.type in (UploadType.VIDEO, UploadType.AUDIO): + token = upload.token + + elif att.type == UploadType.FILE: + json_r = json_loads(upload_file_response) + token = json_r['token'] + + elif att.type == UploadType.IMAGE: + json_r = json_loads(upload_file_response) + json_r_keys = list(json_r['photos'].keys()) + token = json_r['photos'][json_r_keys[0]]['token'] + + return AttachmentUpload( + type=att.type, + payload=AttachmentPayload( + token=token + ) + ) + async def request(self) -> SendedMessage: params = self.bot.params.copy() - json = {} + json = {'attachments': []} if self.chat_id: params['chat_id'] = self.chat_id elif self.user_id: params['user_id'] = self.user_id @@ -49,17 +93,37 @@ class SendMessage(BaseConnection): json['text'] = self.text json['disable_link_preview'] = str(self.disable_link_preview).lower() - if self.attachments: json['attachments'] = \ - [att.model_dump() for att in self.attachments] + if self.attachments: + + for att in self.attachments: + + if isinstance(att, InputMedia): + input_media = await self.__process_input_media(att) + json['attachments'].append( + input_media.model_dump() + ) + else: + json['attachments'].append(att.model_dump()) if not self.link is None: json['link'] = self.link.model_dump() if not self.notify is None: json['notify'] = self.notify if not self.parse_mode is None: json['format'] = self.parse_mode.value - return await super().request( - method=HTTPMethod.POST, - path=ApiPath.MESSAGES, - model=SendedMessage, - params=params, - json=json - ) \ No newline at end of file + response = None + for attempt in range(5): + response = await super().request( + method=HTTPMethod.POST, + path=ApiPath.MESSAGES, + model=SendedMessage, + params=params, + json=json + ) + + if isinstance(response, Error): + if response.raw.get('code') == 'attachment.not.ready': + logger_bot.info(f'Ошибка при отправке загруженного медиа, попытка {attempt+1}, жду 2 секунды') + await asyncio.sleep(2) + continue + + return response + return response \ No newline at end of file diff --git a/maxapi/methods/types/getted_upload_url.py b/maxapi/methods/types/getted_upload_url.py new file mode 100644 index 0000000..3f1756b --- /dev/null +++ b/maxapi/methods/types/getted_upload_url.py @@ -0,0 +1,9 @@ +from typing import Any, Optional +from pydantic import BaseModel + +from ...types.message import Message + + +class GettedUploadUrl(BaseModel): + url: Optional[str] = None + token: Optional[str] = None \ No newline at end of file diff --git a/maxapi/methods/types/upload_file_response.py b/maxapi/methods/types/upload_file_response.py new file mode 100644 index 0000000..9765910 --- /dev/null +++ b/maxapi/methods/types/upload_file_response.py @@ -0,0 +1,5 @@ +from pydantic import BaseModel + + +class UploadFileResponse(BaseModel): + ... \ No newline at end of file diff --git a/maxapi/types/__init__.py b/maxapi/types/__init__.py index f7775f2..dc0703f 100644 --- a/maxapi/types/__init__.py +++ b/maxapi/types/__init__.py @@ -23,7 +23,10 @@ from ..types.attachments.buttons.request_geo_location_button import RequestGeoLo from ..types.command import Command, BotCommand +from input_media import InputMedia + __all__ = [ + InputMedia, BotCommand, CallbackButton, ChatButton, diff --git a/maxapi/types/attachments/attachment.py b/maxapi/types/attachments/attachment.py index a88750b..0475fdb 100644 --- a/maxapi/types/attachments/attachment.py +++ b/maxapi/types/attachments/attachment.py @@ -1,6 +1,8 @@ from typing import List, Optional, Union from pydantic import BaseModel +from ...types.attachments.upload import AttachmentUpload + from ...types.attachments.buttons import InlineButtonUnion from ...types.users import User from ...enums.attachment import AttachmentType @@ -36,6 +38,7 @@ class ButtonsPayload(BaseModel): class Attachment(BaseModel): type: AttachmentType payload: Optional[Union[ + AttachmentUpload, PhotoAttachmentPayload, OtherAttachmentPayload, ContactAttachmentPayload, diff --git a/maxapi/types/attachments/upload.py b/maxapi/types/attachments/upload.py new file mode 100644 index 0000000..165b298 --- /dev/null +++ b/maxapi/types/attachments/upload.py @@ -0,0 +1,14 @@ + + +from pydantic import BaseModel + +from ...enums.upload_type import UploadType + + +class AttachmentPayload(BaseModel): + token: str + + +class AttachmentUpload(BaseModel): + type: UploadType + payload: AttachmentPayload \ No newline at end of file diff --git a/maxapi/types/callback.py b/maxapi/types/callback.py index 1df7eaf..bfb74fc 100644 --- a/maxapi/types/callback.py +++ b/maxapi/types/callback.py @@ -1,10 +1,8 @@ -from typing import List, Optional, Union +from typing import Optional from pydantic import BaseModel from ..types.users import User -from ..types.users import User - class Callback(BaseModel): timestamp: int diff --git a/maxapi/types/chats.py b/maxapi/types/chats.py index 03a830c..d163a53 100644 --- a/maxapi/types/chats.py +++ b/maxapi/types/chats.py @@ -1,23 +1,14 @@ from pydantic import BaseModel, field_validator from typing import Dict, List, Optional -from enum import Enum from datetime import datetime +from ..enums.chat_status import ChatStatus +from ..enums.chat_type import ChatType from ..enums.chat_permission import ChatPermission from ..types.users import User from ..types.message import Message -class ChatType(str, Enum): - DIALOG = "dialog" - CHAT = "chat" - -class ChatStatus(str, Enum): - ACTIVE = "active" - REMOVED = "removed" - LEFT = "left" - CLOSED = "closed" - SUSPENDED = "suspended" class Icon(BaseModel): url: str diff --git a/maxapi/types/errors.py b/maxapi/types/errors.py index 6a8f143..69f2e5a 100644 --- a/maxapi/types/errors.py +++ b/maxapi/types/errors.py @@ -3,4 +3,4 @@ from pydantic import BaseModel class Error(BaseModel): code: int - text: str \ No newline at end of file + raw: dict \ No newline at end of file diff --git a/maxapi/types/input_media.py b/maxapi/types/input_media.py new file mode 100644 index 0000000..c04b12e --- /dev/null +++ b/maxapi/types/input_media.py @@ -0,0 +1,24 @@ +import mimetypes + +from ..enums.upload_type import UploadType + + +class InputMedia: + def __init__(self, path: str): + self.path = path + self.type = self.__detect_file_type(path) + + def __detect_file_type(self, path: str) -> UploadType: + mime_type, _ = mimetypes.guess_type(path) + + if mime_type is None: + return UploadType.FILE + + if mime_type.startswith('video/'): + return UploadType.VIDEO + elif mime_type.startswith('image/'): + return UploadType.IMAGE + elif mime_type.startswith('audio/'): + return UploadType.AUDIO + else: + return UploadType.FILE \ No newline at end of file