diff --git a/bots/handlers/room_handler.py b/bots/handlers/room_handler.py index 61568b9..6d1df0b 100644 --- a/bots/handlers/room_handler.py +++ b/bots/handlers/room_handler.py @@ -1,12 +1,9 @@ # -*- coding: utf-8 -*- """ Обработчик MUC комнат (Multi-User Chat). -- Автоматический вход по приглашению (даже если бот перезагружен – комната сохраняется в БД). +- Автоматический вход по приглашению (комната сохраняется на сервере). - Периодическая проверка присутствия в комнатах и переподключение при необходимости. -- Сохранение JID комнат в PostgreSQL для восстановления после рестарта. - -ВНИМАНИЕ: Все JID комнат должны храниться и сравниваться как строки (bare JID), -чтобы избежать ошибок типов при работе с asyncpg и slixmpp. +- Загрузка комнат с сервера при старте. """ import logging @@ -16,7 +13,7 @@ logger = logging.getLogger(__name__) class RoomHandler: - """Управление комнатами: приглашения, реджоин, сохранение в БД.""" + """Управление комнатами: приглашения, реджоин, сохранение в БД через RAG-сервер.""" def __init__(self, bot): self.bot = bot @@ -24,27 +21,20 @@ class RoomHandler: async def accept_invite(self, inv): """ Обработчик события groupchat_invite. - Автоматически входит в комнату, добавляет её в список rooms и сохраняет в БД. - - Аргументы: - inv: объект приглашения (содержит атрибуты 'room' или 'from') + Автоматически входит в комнату, добавляет её на сервер. """ room = inv.get('room', inv.get('from')) if not room: logger.warning("Приглашение не содержит идентификатора комнаты") return - - # Преобразуем в строку bare JID (без ресурса) - if hasattr(room, 'bare'): - room_str = room.bare - else: - room_str = str(room) - + room_str = room.bare if hasattr(room, 'bare') else str(room) logger.info(f"Приглашение в комнату {room_str}, входим.") - # Если комната ещё не в списке бота – добавляем - if room_str not in self.bot.rooms: - self.bot.rooms.append(room_str) + # Сохраняем комнату на сервере + try: + await self.bot.rag_client.add_room(room_str) + except Exception as e: + logger.error(f"Ошибка сохранения комнаты на сервере: {e}") # Входим в MUC-комнату await self.bot.plugin['xep_0045'].join_muc(room_str, self.bot.boundjid.user) @@ -52,22 +42,24 @@ class RoomHandler: async def rejoin_loop(self): """ Бесконечный цикл переподключения к комнатам. - Проверяет, в каких комнатах бот состоит, и если его нет – переподключается. + Загружает список комнат с сервера и входит в те, где бот отсутствует. """ while True: await asyncio.sleep(60) - # Получаем список комнат, где бот присутствует joined_rooms = set() try: - if hasattr(self.bot.plugin['xep_0045'], 'get_joined_rooms'): - joined_rooms = set(self.bot.plugin['xep_0045'].get_joined_rooms()) - else: - joined_rooms = {str(r) for r in self.bot.plugin['xep_0045'].rooms.keys()} + joined_rooms = {str(r) for r in self.bot.plugin['xep_0045'].rooms.keys()} except Exception as e: logger.debug(f"Ошибка получения списка комнат: {e}") continue - for room in self.bot.rooms: + try: + rooms = await self.bot.rag_client.get_rooms() + except Exception as e: + logger.error(f"Ошибка загрузки комнат с сервера: {e}") + continue + + for room in rooms: if room not in joined_rooms: logger.info(f"Попытка повторного входа в комнату {room}...") try: @@ -75,17 +67,17 @@ class RoomHandler: await asyncio.sleep(1) except Exception as e: logger.error(f"Ошибка входа в {room}: {e}") - + async def on_kicked(self, presence): """Обработчик события, когда бота исключают из комнаты.""" room = presence['from'].bare logger.info(f"Бот был исключён из комнаты {room}") - if room in self.bot.rooms: - self.bot.rooms.remove(room) + # Комната остаётся на сервере, но бот перестаёт в ней состоять. + # При следующем цикле rejoin он войдёт снова, если комната есть в списке. async def on_banned(self, presence): """Обработчик события, когда бота банят в комнате.""" room = presence['from'].bare logger.info(f"Бот был забанен в комнате {room}") - if room in self.bot.rooms: - self.bot.rooms.remove(room) \ No newline at end of file + # Бот не сможет войти, но комната остаётся на сервере. + # Можно удалить комнату с сервера, если нужно. \ No newline at end of file