From 770445feaa03fe76afaff5607336980c878b518c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=98=D0=B3=D0=BE=D1=80=D1=8C=20=D0=91=D0=B0=D0=BD=D0=B4?= =?UTF-8?q?=D1=83=D1=80=D0=B8=D1=81=D1=82?= Date: Sat, 16 May 2026 12:41:54 +1000 Subject: [PATCH] =?UTF-8?q?=D0=B4=D0=BE=D0=B1=D0=B0=D0=B2=D0=B8=D0=BB=20?= =?UTF-8?q?=D0=B0=D1=82=D0=BE=D1=81=D1=82=D0=B0=D1=80=D1=82=20=D0=B2=D1=81?= =?UTF-8?q?=D0=B5=D1=85=20=D1=81=D0=B0=D0=B9=D1=82=D0=BE=D0=B2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- main.py | 28 +++++++++++++++++++++++++++- parsers/__init__.py | 3 ++- parsers/universal.py | 7 +++++++ work_parser.py | 19 +++++++++++++++++++ 4 files changed, 55 insertions(+), 2 deletions(-) diff --git a/main.py b/main.py index 64bd629..78096c6 100644 --- a/main.py +++ b/main.py @@ -4,6 +4,7 @@ Parser API - Точка входа приложения from contextlib import asynccontextmanager from fastapi import FastAPI import uvicorn +from work_parser import get_true_sources from config import ( APP_TITLE, @@ -16,10 +17,11 @@ from config import ( SCHEDULED_PARSER_2_MINUTE ) from apscheduler.schedulers.asyncio import AsyncIOScheduler -from parsers import scheduled_parser_1, scheduled_parser_2 +from parsers import scheduled_parser_1, scheduled_parser_2, scheduled_parser_universal from api import setup_routes + # Инициализация планировщика scheduler = AsyncIOScheduler() @@ -30,12 +32,36 @@ async def lifespan(app: FastAPI): # Startup scheduler.add_job(scheduled_parser_1, "cron", hour=SCHEDULED_PARSER_1_HOUR, minute=SCHEDULED_PARSER_1_MINUTE) scheduler.add_job(scheduled_parser_2, "cron", hour=SCHEDULED_PARSER_2_HOUR, minute=SCHEDULED_PARSER_2_MINUTE) + + # Получаем все источники и распределяем их равномерно по 24 часам + sources = get_true_sources().items() + num_sources = len(sources) + + if num_sources > 0: + total_minutes_per_day = 24 * 60 + minutes_per_source = total_minutes_per_day / num_sources + + for idx, (url, promt) in enumerate(sources): + total_minutes = int(idx * minutes_per_source) + scheduled_hour = total_minutes // 60 + scheduled_minute = total_minutes % 60 + + # Для универсального парсера нужно передавать url и promt как аргументы + scheduler.add_job( + scheduled_parser_universal, + "cron", + hour=scheduled_hour, + minute=scheduled_minute, + args=[url, promt] + ) + scheduler.start() yield # Shutdown scheduler.shutdown() + # Создание приложения FastAPI app = FastAPI( title=APP_TITLE, diff --git a/parsers/__init__.py b/parsers/__init__.py index 825c00d..028e6d5 100644 --- a/parsers/__init__.py +++ b/parsers/__init__.py @@ -15,5 +15,6 @@ __all__ = [ 'start_pars_two_istochnik', 'scheduled_parser_2', 'UniversalParser', - 'start_pars_all_istochnik' + 'start_pars_all_istochnik', + 'scheduled_parser_universal' ] diff --git a/parsers/universal.py b/parsers/universal.py index a76b10f..2dfd328 100644 --- a/parsers/universal.py +++ b/parsers/universal.py @@ -122,3 +122,10 @@ def start_pars_all_istochnik(url: str, promt: str) -> None: """ parser = UniversalParser(url, promt) parser.parse() + + +def scheduled_parser_universal(url: str, promt: str) -> None: + """ + Функция для автоматического запуска универсального парсера по расписанию + """ + start_pars_all_istochnik(url, promt) diff --git a/work_parser.py b/work_parser.py index c220edd..d6e8822 100644 --- a/work_parser.py +++ b/work_parser.py @@ -409,6 +409,25 @@ def get_all_sources(category: str): return {"error": str(e), "sources": []} +def get_true_sources(): + """Возвращает все записи из таблицы sourse. Сначала показываются записи со status=true""" + conn = get_connection() + try: + with conn.cursor(cursor_factory=RealDictCursor) as cur: + cur.execute(""" + SELECT * FROM sourse + WHERE status = true + """) + rows = cur.fetchall() + sources = {} + for row in rows: + sources.update({row["url"]: row["promt"]}) + return sources + except Exception as e: + print(f"Ошибка при получении источников: {e}") + return {"error": str(e), "sources": []} + + def update_source_status(url: str, status: bool = True): """Обновляет статус источника по URL""" conn = get_connection()