From ca0a8314e60d0e2c7447a9bc94240a04e7a73653 Mon Sep 17 00:00:00 2001 From: Markov Andrey Date: Tue, 30 Jun 2026 12:35:40 +0000 Subject: [PATCH] Add new file --- bots/handlers/health_handler.py | 97 +++++++++++++++++++++++++++++++++ 1 file changed, 97 insertions(+) create mode 100644 bots/handlers/health_handler.py diff --git a/bots/handlers/health_handler.py b/bots/handlers/health_handler.py new file mode 100644 index 0000000..6ee2747 --- /dev/null +++ b/bots/handlers/health_handler.py @@ -0,0 +1,97 @@ +# -*- coding: utf-8 -*- +""" +Обработчик здоровья системы: периодическая очистка временных файлов, +проверка подключения к PostgreSQL и Qdrant. + +Используется только на стороне клиентов (ботов) для локальной очистки. +""" + +import asyncio +import logging +import os +from datetime import datetime + +logger = logging.getLogger(__name__) + + +class HealthHandler: + """ + Периодические задачи: + - Очистка временной директории (temp_dir) и upload_dir. + - Очистка постоянных пользовательских файлов (data/user_*). + - Healthcheck подключения к PostgreSQL и Qdrant (раз в час). + """ + + def __init__(self, bot): + self.bot = bot + + # ------------------------------------------------------------------ + # Цикл очистки файлов + # ------------------------------------------------------------------ + + async def cleanup_loop(self): + """ + Бесконечный цикл очистки временных файлов. + Интервал и сроки хранения берутся из конфига (cleanup.interval_seconds, + temp_cleanup_days, upload_cleanup_days, user_data_cleanup_days). + """ + while True: + await asyncio.sleep(self.bot.config.cleanup_interval) + try: + def sync_cleanup(): + # Очистка временной папки (temp_dir) + self.bot.files.cleanup_old_files(days=self.bot.config.temp_cleanup_days) + + # Очистка папки upload_dir + upload_dir = self.bot.config.upload_dir + if upload_dir.exists(): + now = datetime.now().timestamp() + for root, dirs, files in os.walk(upload_dir, topdown=False): + for name in files: + file_path = os.path.join(root, name) + try: + if os.path.getmtime(file_path) < now - self.bot.config.upload_cleanup_days * 86400: + os.remove(file_path) + except Exception: + pass + for name in dirs: + dir_path = os.path.join(root, name) + try: + if not os.listdir(dir_path): + os.rmdir(dir_path) + except Exception: + pass + + # Очистка постоянных пользовательских файлов в data/ + data_dir = self.bot.config.data_dir + if data_dir.exists(): + now = datetime.now().timestamp() + days = getattr(self.bot.config, 'user_data_cleanup_days', 30) + for file_path in data_dir.iterdir(): + if file_path.is_file() and file_path.name.startswith('user_'): + if now - file_path.stat().st_mtime > days * 86400: + file_path.unlink() + logger.debug(f"Удалён старый пользовательский файл: {file_path.name}") + + await asyncio.to_thread(sync_cleanup) + logger.info("Очистка временных файлов выполнена") + except Exception as e: + logger.error(f"Ошибка в цикле очистки: {e}") + + # ------------------------------------------------------------------ + # Мониторинг состояния БД и Qdrant + # ------------------------------------------------------------------ + + async def database_health_logger(self): + """ + Бесконечный цикл: раз в час проверяет соединение с PostgreSQL и Qdrant, + логирует результат (OK или FAILED). + """ + while True: + await asyncio.sleep(3600) + + # --- Проверка PostgreSQL (через RAG-сервер, бот не имеет прямой БД) --- + # В новой архитектуре бот не имеет прямого доступа к БД, + # поэтому healthcheck перенесён на RAG-сервер. + # Здесь мы просто логируем, что проверка пропущена. + logger.debug("Healthcheck БД выполняется на RAG-сервере") \ No newline at end of file