--- description: "Обработка ошибок, исключения и логирование" alwaysApply: false --- # Обработка ошибок и исключений ## Иерархия исключений Каждый модуль должен иметь свой файл `exceptions.py` с иерархией исключений: ```python # Базовое исключение модуля class ModuleError(Exception): """Базовое исключение для модуля""" pass # Специализированные исключения class UserNotFoundError(ModuleError): """Исключение при отсутствии пользователя""" pass class InvalidInputError(ModuleError): """Исключение при некорректном вводе данных""" pass ``` ## Обработка в Handlers ### Паттерн try-except ```python @router.message(...) async def handler(message: types.Message, state: FSMContext, **kwargs): try: # Основная логика service = SomeService(bot_db, settings) result = await service.do_something() await message.answer("Успех") except UserNotFoundError as e: # Обработка специфичной ошибки await message.answer(f"Пользователь не найден: {str(e)}") logger.warning(f"Пользователь не найден: {e}") except InvalidInputError as e: # Обработка ошибки валидации await message.answer(f"Некорректный ввод: {str(e)}") logger.warning(f"Некорректный ввод: {e}") except Exception as e: # Обработка неожиданных ошибок await handle_error(message, e, state) logger.error(f"Неожиданная ошибка в handler: {e}", exc_info=True) ``` ### Декоратор error_handler Некоторые модули используют декоратор `@error_handler` для автоматической обработки: ```python from .decorators import error_handler @error_handler @router.message(...) async def handler(...): # Код handler # Ошибки автоматически логируются и отправляются в important_logs ... ``` ## Обработка в Services ```python class SomeService: async def do_something(self): try: # Бизнес-логика data = await self.bot_db.get_data() if not data: raise UserNotFoundError("Пользователь не найден") return self._process(data) except UserNotFoundError: # Пробрасываем специфичные исключения дальше raise except Exception as e: # Логируем и пробрасываем неожиданные ошибки logger.error(f"Ошибка в сервисе: {e}", exc_info=True) raise ``` ## Логирование ### Использование logger Всегда используйте `logs.custom_logger.logger`: ```python from logs.custom_logger import logger # Информационные сообщения logger.info(f"Пользователь {user_id} выполнил действие") # Предупреждения logger.warning(f"Попытка доступа к несуществующему ресурсу: {resource_id}") # Ошибки logger.error(f"Ошибка при выполнении операции: {e}") # Ошибки с traceback logger.error(f"Критическая ошибка: {e}", exc_info=True) ``` ### Уровни логирования - `logger.debug()` - отладочная информация - `logger.info()` - информационные сообщения о работе - `logger.warning()` - предупреждения о потенциальных проблемах - `logger.error()` - ошибки, требующие внимания - `logger.critical()` - критические ошибки ## Метрики ошибок Декоратор `@track_errors` автоматически отслеживает ошибки: ```python @track_errors("module_name", "method_name") async def some_method(): # Ошибки автоматически записываются в метрики ... ``` ## Централизованная обработка ### В admin handlers Используется функция `handle_admin_error()`: ```python from helper_bot.handlers.admin.utils import handle_admin_error try: # Код except Exception as e: await handle_admin_error(message, e, state, "context_name") ``` ### В других модулях Создавайте аналогичные утилиты для централизованной обработки ошибок модуля. ## Best Practices 1. **Всегда логируйте ошибки** перед пробросом или обработкой 2. **Используйте специфичные исключения** вместо общих `Exception` 3. **Пробрасывайте исключения** из сервисов в handlers для обработки 4. **Не глотайте исключения** без логирования 5. **Используйте `exc_info=True`** для логирования traceback критических ошибок 6. **Обрабатывайте ошибки на правильном уровне**: бизнес-логика в сервисах, пользовательские сообщения в handlers