add proxy for tg and fix auth
This commit is contained in:
+56
-66
@@ -2,12 +2,12 @@
|
||||
Сохранение и загрузка задач между перезапусками.
|
||||
"""
|
||||
|
||||
import json
|
||||
import asyncio
|
||||
import json
|
||||
import logging
|
||||
from pathlib import Path
|
||||
from datetime import datetime
|
||||
from typing import Dict, Optional
|
||||
from typing import Dict
|
||||
|
||||
from managers.task_manager import TaskParams
|
||||
|
||||
@@ -16,14 +16,13 @@ logger = logging.getLogger(__name__)
|
||||
|
||||
class TaskStorage:
|
||||
"""Хранилище задач в JSON файле."""
|
||||
|
||||
|
||||
def __init__(self, file_path: str = "data/tasks.json"):
|
||||
self.file_path = Path(file_path)
|
||||
self.file_path.parent.mkdir(parents=True, exist_ok=True)
|
||||
self._lock = asyncio.Lock()
|
||||
|
||||
|
||||
def _params_to_dict(self, params: TaskParams) -> dict:
|
||||
"""Конвертирует TaskParams в словарь."""
|
||||
return {
|
||||
"url": params.url,
|
||||
"task_type": params.task_type,
|
||||
@@ -47,9 +46,8 @@ class TaskStorage:
|
||||
"chat_id": params.chat_id,
|
||||
"started_at": params.started_at.isoformat() if params.started_at else None,
|
||||
}
|
||||
|
||||
|
||||
def _dict_to_params(self, data: dict) -> TaskParams:
|
||||
"""Конвертирует словарь в TaskParams."""
|
||||
params = TaskParams(
|
||||
url=data.get("url", ""),
|
||||
task_type=data.get("task_type", "visit"),
|
||||
@@ -72,58 +70,51 @@ class TaskStorage:
|
||||
links_found=data.get("links_found", 0),
|
||||
chat_id=data.get("chat_id"),
|
||||
)
|
||||
|
||||
if data.get("started_at"):
|
||||
try:
|
||||
params.started_at = datetime.fromisoformat(data["started_at"])
|
||||
except (ValueError, TypeError) as e:
|
||||
logger.warning(f"Failed to parse started_at: {e}")
|
||||
|
||||
return params
|
||||
|
||||
|
||||
def _save_sync(self, data: dict) -> None:
|
||||
with open(self.file_path, "w", encoding="utf-8") as f:
|
||||
json.dump(data, f, ensure_ascii=False, indent=2)
|
||||
|
||||
def _load_sync(self) -> dict:
|
||||
if not self.file_path.exists():
|
||||
return {}
|
||||
with open(self.file_path, "r", encoding="utf-8") as f:
|
||||
return json.load(f)
|
||||
|
||||
async def save_tasks(self, tasks: Dict[str, TaskParams]) -> None:
|
||||
"""Сохраняет все задачи в файл."""
|
||||
async with self._lock:
|
||||
try:
|
||||
data = {}
|
||||
for task_id, params in tasks.items():
|
||||
data[task_id] = self._params_to_dict(params)
|
||||
|
||||
with open(self.file_path, 'w', encoding='utf-8') as f:
|
||||
json.dump(data, f, ensure_ascii=False, indent=2)
|
||||
|
||||
data = {tid: self._params_to_dict(p) for tid, p in tasks.items()}
|
||||
await asyncio.to_thread(self._save_sync, data)
|
||||
logger.info(f"💾 Saved {len(data)} tasks to {self.file_path}")
|
||||
except Exception as e:
|
||||
logger.error(f"Save error: {e}")
|
||||
|
||||
|
||||
async def load_tasks(self) -> Dict[str, TaskParams]:
|
||||
"""Загружает задачи из файла."""
|
||||
if not self.file_path.exists():
|
||||
logger.info("No saved tasks found")
|
||||
return {}
|
||||
|
||||
try:
|
||||
with open(self.file_path, 'r', encoding='utf-8') as f:
|
||||
data = json.load(f)
|
||||
|
||||
tasks = {}
|
||||
for task_id, params_data in data.items():
|
||||
tasks[task_id] = self._dict_to_params(params_data)
|
||||
|
||||
data = await asyncio.to_thread(self._load_sync)
|
||||
if not data:
|
||||
logger.info("No saved tasks found")
|
||||
return {}
|
||||
tasks = {tid: self._dict_to_params(d) for tid, d in data.items()}
|
||||
logger.info(f"📂 Loaded {len(tasks)} tasks from {self.file_path}")
|
||||
return tasks
|
||||
except Exception as e:
|
||||
logger.error(f"Load error: {e}")
|
||||
return {}
|
||||
|
||||
|
||||
async def save_task(self, task_id: str, params: TaskParams) -> None:
|
||||
"""Сохраняет одну задачу (добавляет к существующим)."""
|
||||
tasks = await self.load_tasks()
|
||||
tasks[task_id] = params
|
||||
await self.save_tasks(tasks)
|
||||
|
||||
|
||||
async def delete_task(self, task_id: str) -> None:
|
||||
"""Удаляет задачу из файла."""
|
||||
tasks = await self.load_tasks()
|
||||
if task_id in tasks:
|
||||
del tasks[task_id]
|
||||
@@ -132,46 +123,45 @@ class TaskStorage:
|
||||
|
||||
class ChatStorage:
|
||||
"""Хранилище привязки стримеров к чатам."""
|
||||
|
||||
|
||||
def __init__(self, file_path: str = "data/chats.json"):
|
||||
self.file_path = Path(file_path)
|
||||
self.file_path.parent.mkdir(parents=True, exist_ok=True)
|
||||
self._lock = asyncio.Lock()
|
||||
|
||||
async def get_chat_streamers(self, chat_id: int) -> list:
|
||||
"""Получает список стримеров для чата."""
|
||||
data = await self._load()
|
||||
return data.get(str(chat_id), [])
|
||||
|
||||
async def add_streamer(self, chat_id: int, channel: str) -> None:
|
||||
"""Добавляет стримера в чат."""
|
||||
data = await self._load()
|
||||
key = str(chat_id)
|
||||
if key not in data:
|
||||
data[key] = []
|
||||
if channel not in data[key]:
|
||||
data[key].append(channel)
|
||||
await self._save(data)
|
||||
|
||||
async def remove_streamer(self, chat_id: int, channel: str) -> None:
|
||||
"""Удаляет стримера из чата."""
|
||||
data = await self._load()
|
||||
key = str(chat_id)
|
||||
if key in data and channel in data[key]:
|
||||
data[key].remove(channel)
|
||||
await self._save(data)
|
||||
|
||||
async def _load(self) -> dict:
|
||||
|
||||
def _load_sync(self) -> dict:
|
||||
if not self.file_path.exists():
|
||||
return {}
|
||||
try:
|
||||
with open(self.file_path, 'r', encoding='utf-8') as f:
|
||||
with open(self.file_path, "r", encoding="utf-8") as f:
|
||||
return json.load(f)
|
||||
except (json.JSONDecodeError, IOError) as e:
|
||||
logger.warning(f"Failed to load chats: {e}")
|
||||
return {}
|
||||
|
||||
async def _save(self, data: dict) -> None:
|
||||
|
||||
def _save_sync(self, data: dict) -> None:
|
||||
with open(self.file_path, "w", encoding="utf-8") as f:
|
||||
json.dump(data, f, ensure_ascii=False, indent=2)
|
||||
|
||||
async def get_chat_streamers(self, chat_id: int) -> list:
|
||||
async with self._lock:
|
||||
with open(self.file_path, 'w', encoding='utf-8') as f:
|
||||
json.dump(data, f, ensure_ascii=False, indent=2)
|
||||
data = await asyncio.to_thread(self._load_sync)
|
||||
return data.get(str(chat_id), [])
|
||||
|
||||
async def add_streamer(self, chat_id: int, channel: str) -> None:
|
||||
async with self._lock:
|
||||
data = await asyncio.to_thread(self._load_sync)
|
||||
key = str(chat_id)
|
||||
if key not in data:
|
||||
data[key] = []
|
||||
if channel not in data[key]:
|
||||
data[key].append(channel)
|
||||
await asyncio.to_thread(self._save_sync, data)
|
||||
|
||||
async def remove_streamer(self, chat_id: int, channel: str) -> None:
|
||||
async with self._lock:
|
||||
data = await asyncio.to_thread(self._load_sync)
|
||||
key = str(chat_id)
|
||||
if key in data and channel in data[key]:
|
||||
data[key].remove(channel)
|
||||
await asyncio.to_thread(self._save_sync, data)
|
||||
|
||||
Reference in New Issue
Block a user