This commit is contained in:
parent
88c4c84dec
commit
a8723bb3ee
4 changed files with 43 additions and 4 deletions
|
|
@ -12,9 +12,12 @@
|
|||
"""
|
||||
from __future__ import annotations
|
||||
|
||||
import logging
|
||||
from abc import ABC, abstractmethod
|
||||
from dataclasses import dataclass
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
|
||||
# ── Агностичное представление клавиатуры ──────────────────────────────────────
|
||||
|
||||
|
|
@ -101,39 +104,48 @@ class TelegramChannelNotifier(Notifier):
|
|||
# ── Реализация интерфейса ──────────────────────────────────────────────────
|
||||
|
||||
def send(self, text: str, keyboard: Keyboard | None = None) -> int:
|
||||
log.info("Telegram send_message → channel %s", self._channel_id)
|
||||
msg = self._bot.send_message(
|
||||
self._channel_id, text,
|
||||
parse_mode="Markdown",
|
||||
disable_web_page_preview=True,
|
||||
reply_markup=self._to_markup(keyboard),
|
||||
)
|
||||
log.info("Telegram send_message OK, message_id=%s", msg.message_id)
|
||||
return msg.message_id
|
||||
|
||||
def edit_text(self, message_id: int, text: str, keyboard: Keyboard | None = None):
|
||||
log.info("Telegram edit_message_text → message_id=%s", message_id)
|
||||
self._bot.edit_message_text(
|
||||
text, self._channel_id, message_id,
|
||||
parse_mode="Markdown",
|
||||
disable_web_page_preview=True,
|
||||
reply_markup=self._to_markup(keyboard),
|
||||
)
|
||||
log.info("Telegram edit_message_text OK, message_id=%s", message_id)
|
||||
|
||||
def edit_keyboard(self, message_id: int, keyboard: Keyboard | None):
|
||||
log.info("Telegram edit_message_reply_markup → message_id=%s", message_id)
|
||||
self._bot.edit_message_reply_markup(
|
||||
self._channel_id, message_id,
|
||||
reply_markup=self._to_markup(keyboard),
|
||||
)
|
||||
|
||||
def delete(self, message_id: int):
|
||||
log.info("Telegram delete_message → message_id=%s", message_id)
|
||||
try:
|
||||
self._bot.delete_message(self._channel_id, message_id)
|
||||
except Exception:
|
||||
pass
|
||||
log.info("Telegram delete_message OK, message_id=%s", message_id)
|
||||
except Exception as e:
|
||||
log.warning("Telegram delete_message failed (message_id=%s): %s", message_id, e)
|
||||
|
||||
def send_animation(self, url: str, disable_notification: bool = True) -> int:
|
||||
log.info("Telegram send_animation → channel %s", self._channel_id)
|
||||
msg = self._bot.send_animation(
|
||||
self._channel_id, url,
|
||||
disable_notification=disable_notification,
|
||||
)
|
||||
log.info("Telegram send_animation OK, message_id=%s", msg.message_id)
|
||||
return msg.message_id
|
||||
|
||||
def is_stale_error(self, exc: Exception) -> bool:
|
||||
|
|
|
|||
|
|
@ -50,7 +50,8 @@ def recreate_post(
|
|||
Изменения (• ...) дедуплицируются по тексту.
|
||||
Комментарии (💬 ...) и описания (📝 ...) добавляются всегда.
|
||||
"""
|
||||
notifier = get_notifier()
|
||||
notifier = get_notifier()
|
||||
|
||||
stored = database.get_stored_events(task_id)
|
||||
stored_set = set(stored)
|
||||
|
||||
|
|
|
|||
|
|
@ -38,10 +38,17 @@ access_log_format = '%(h)s "%(r)s" %(s)s %(b)s %(D)sµs'
|
|||
|
||||
def on_starting(server):
|
||||
"""Инициализация до форка воркеров (выполняется в мастер-процессе)."""
|
||||
import logging
|
||||
import config
|
||||
import database
|
||||
from intradesk import reference
|
||||
|
||||
logging.basicConfig(
|
||||
level=logging.INFO,
|
||||
format="%(asctime)s [%(levelname)s] %(name)s: %(message)s",
|
||||
handlers=[logging.StreamHandler()],
|
||||
)
|
||||
|
||||
os.makedirs(os.path.dirname(config.DB_FILE), exist_ok=True)
|
||||
database.init_db()
|
||||
reference.seed_static()
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
import json
|
||||
import logging
|
||||
import os
|
||||
import queue
|
||||
import threading
|
||||
|
||||
from flask import Flask, Response, jsonify, render_template, request, stream_with_context, abort
|
||||
|
|
@ -19,6 +20,24 @@ from intradesk.handler import handle_webhook
|
|||
log = logging.getLogger(__name__)
|
||||
app = Flask(__name__, template_folder=os.path.join(os.path.dirname(__file__), "templates"))
|
||||
|
||||
# ── Очередь вебхуков (последовательная обработка) ─────────────────────────────
|
||||
|
||||
_webhook_queue: queue.Queue = queue.Queue()
|
||||
|
||||
|
||||
def _webhook_worker():
|
||||
while True:
|
||||
data = _webhook_queue.get()
|
||||
try:
|
||||
handle_webhook(data)
|
||||
except Exception:
|
||||
log.exception("Unhandled error in webhook worker")
|
||||
finally:
|
||||
_webhook_queue.task_done()
|
||||
|
||||
|
||||
threading.Thread(target=_webhook_worker, daemon=True, name="webhook-worker").start()
|
||||
|
||||
|
||||
# ── Авторизация ────────────────────────────────────────────────────────────────
|
||||
|
||||
|
|
@ -97,7 +116,7 @@ def webhook():
|
|||
if not data:
|
||||
return jsonify({"error": "Invalid JSON"}), 400
|
||||
|
||||
threading.Thread(target=handle_webhook, args=(data,), daemon=True).start()
|
||||
_webhook_queue.put(data)
|
||||
return jsonify({"ok": True}), 200
|
||||
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue