Как можно узнать общее количество сообщений в личном чате с ботом или ID последнего обработанного сообщения, зная ID пользователя?

Не имеет значения, было ли сообщение отправлено ботом или пользователем. К сожалению, я не могу рассматривать решения, основанные на использовании баз данных. Я хотел бы, чтобы метод работал как для aiogram 3, так и для aiogram 2.25. <br/> <br/> В настоящее время я нашел временное решение: отправляю сообщение, получаю его ID и сразу же удаляю. Однако из-за этого последующие сообщения будут иметь другой ID, что является недопустимым.
  • 16 декабря 2024 г. 13:03
Ответы на вопрос 2
Если у вас нет доступа к базе данных и вы хотите узнать общее количество сообщений в личном чате с ботом или ID последнего обработанного сообщения, то, к сожалению, возможности API Telegram ограничены. Однако можно предложить некоторые альтернативные способы.

### Альтернативные подходы:

1. **Хранение состояния в памяти:** Если вы не хотите использовать базу данных, вы можете реализовать хранение состояния в памяти. Простой пример использования словаря для хранения ID последнего сообщения и общего количества сообщений:

   ```python
   from aiogram import Bot, Dispatcher, types
   from aiogram.contrib.fsm_storage.memory import MemoryStorage
   from aiogram.utils import executor

   bot = Bot(token='YOUR_BOT_TOKEN')
   dp = Dispatcher(bot, storage=MemoryStorage())

   chat_data = {}

   @dp.message_handler()
   async def echo(message: types.Message):
       user_id = message.from_user.id

       if user_id not in chat_data:
           chat_data[user_id] = {'message_count': 0, 'last_message_id': None}

       # Увеличиваем счетчик сообщений
       chat_data[user_id]['message_count'] += 1
       chat_data[user_id]['last_message_id'] = message.message_id

       # Отправляем ответ, если нужно
       await message.answer(f"Общее количество сообщений: {chat_data[user_id]['message_count']}, ID последнего сообщения: {chat_data[user_id]['last_message_id']}.")

   if __name__ == '__main__':
       executor.start_polling(dp, skip_updates=True)
   ```

2. **Сохранение в файле:** Если вам нужно хранить данные устойчиво между запусками бота, вы можете сохранять их в файл (например, JSON). Это будет аналог базам данных, но без необходимости в сложной системе управления.

   ```python
   import json
   import os

   def load_chat_data():
       if os.path.exists('chat_data.json'):
           with open('chat_data.json', 'r') as f:
               return json.load(f)
       return {}

   def save_chat_data(data):
       with open('chat_data.json', 'w') as f:
           json.dump(data, f)

   # В основной части кода
   chat_data = load_chat_data()

   @dp.message_handler()
   async def echo(message: types.Message):
       user_id = str(message.from_user.id)

       if user_id not in chat_data:
           chat_data[user_id] = {'message_count': 0, 'last_message_id': None}

       chat_data[user_id]['message_count'] += 1
       chat_data[user_id]['last_message_id'] = message.message_id

       save_chat_data(chat_data)

       await message.answer(f"Общее количество сообщений: {chat_data[user_id]['message_count']}, ID последнего сообщения: {chat_data[user_id]['last_message_id']}.")
   ```

### Объяснение

- В первом примере данные хранятся в оперативной памяти приложения, и чересчур трудно будет сохранять состояние между перезапусками.
- Во втором примере данные сериализуются в JSON файл, что позволяет сохранить состояния между запусками бота.

С помощью этих двух подходов вы сможете отслеживать количество и ID сообщений, избегая непосредственного использования баз данных. Выбор метода зависит от того, насколько устойчивая должна быть система хранения данных.
...
bot = Bot(token=...)
...
async def get_chat_history(user_id: int):
    updates = await bot.get_updates()
    chat_messages = [update.message for update in updates if update.message and update.message.chat.id == user_id]
    return len(chat_messages), chat_messages[-1].message_id if chat_messages else None

Возвращает список, в котором нулевой элемент - кол-во сообщений, первый - id сообщения, если таковое было (если не было, то None)
Похожие вопросы