fix(telegram): 修復 Signal Worker 流程 Telegram 通知斷鏈
問題: - Phase 6 Signal Worker 新架構沒有整合 Telegram 推送 - 決策就緒時 Telegram 完全沒收到通知 - 這是嚴重的監控盲點! 修復: - 新增 _push_decision_to_telegram() 推送函數 - DecisionManager 決策 READY 時自動推送 - 非阻塞執行 (asyncio.create_task) Telegram 通知內容: - 告警來源 (LLM/Expert System) - 受影響服務 - 建議動作 - 風險等級 - 信心分數 Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -28,12 +28,81 @@ from uuid import uuid4
|
||||
import structlog
|
||||
|
||||
from src.core.redis_client import get_redis
|
||||
from src.core.config import settings
|
||||
from src.models.incident import Incident
|
||||
from src.services.openclaw import get_openclaw
|
||||
|
||||
logger = structlog.get_logger(__name__)
|
||||
|
||||
|
||||
# =============================================================================
|
||||
# Telegram 推送 (Phase 6.5: 決策就緒通知)
|
||||
# =============================================================================
|
||||
|
||||
async def _push_decision_to_telegram(
|
||||
incident: Incident,
|
||||
proposal_data: dict[str, Any],
|
||||
) -> None:
|
||||
"""
|
||||
決策就緒時推送到 Telegram
|
||||
|
||||
Phase 6.5: 整合 Signal Worker 流程與 Telegram 通知
|
||||
"""
|
||||
try:
|
||||
# 延遲導入避免循環依賴
|
||||
from src.services.telegram_gateway import get_telegram_gateway, TelegramGatewayError
|
||||
|
||||
# 檢查是否有設定 Bot Token
|
||||
if not settings.OPENCLAW_TG_BOT_TOKEN:
|
||||
logger.debug(
|
||||
"telegram_push_skipped",
|
||||
reason="Bot token not configured",
|
||||
incident_id=incident.incident_id,
|
||||
)
|
||||
return
|
||||
|
||||
gateway = get_telegram_gateway()
|
||||
|
||||
# 從 proposal_data 提取資料
|
||||
target = incident.affected_services[0] if incident.affected_services else "unknown"
|
||||
risk_level = proposal_data.get("risk_level", "medium")
|
||||
action = proposal_data.get("action", proposal_data.get("kubectl_command", ""))
|
||||
description = proposal_data.get("description", "")
|
||||
reasoning = proposal_data.get("reasoning", "")
|
||||
confidence = proposal_data.get("confidence", 0.75)
|
||||
source = proposal_data.get("source", "unknown")
|
||||
|
||||
# 建立 approval_id (使用 incident_id 作為追蹤)
|
||||
approval_id = f"INC-{incident.incident_id}"
|
||||
|
||||
await gateway.send_approval_card(
|
||||
approval_id=approval_id,
|
||||
risk_level=risk_level,
|
||||
resource_name=target[:50],
|
||||
root_cause=f"[{source.upper()}] {reasoning[:80]}" if reasoning else description[:100],
|
||||
suggested_action=action[:50] if action else "待分析",
|
||||
estimated_downtime="5-15 min",
|
||||
primary_responsibility="INFRA",
|
||||
confidence=confidence,
|
||||
namespace=incident.signals[0].labels.get("namespace", "default") if incident.signals else "default",
|
||||
)
|
||||
|
||||
logger.info(
|
||||
"telegram_decision_pushed",
|
||||
incident_id=incident.incident_id,
|
||||
source=source,
|
||||
risk_level=risk_level,
|
||||
)
|
||||
|
||||
except Exception as e:
|
||||
# Telegram 失敗不影響主流程
|
||||
logger.warning(
|
||||
"telegram_decision_push_failed",
|
||||
incident_id=incident.incident_id,
|
||||
error=str(e),
|
||||
)
|
||||
|
||||
|
||||
# =============================================================================
|
||||
# Decision States
|
||||
# =============================================================================
|
||||
@@ -298,6 +367,13 @@ class DecisionManager:
|
||||
# 4. 儲存最終結果
|
||||
await self._save_token(token)
|
||||
|
||||
# 5. Phase 6.5: 推送到 Telegram (非阻塞)
|
||||
if token.state == DecisionState.READY and token.proposal_data:
|
||||
# 使用 asyncio.create_task 非阻塞執行
|
||||
asyncio.create_task(
|
||||
_push_decision_to_telegram(incident, token.proposal_data)
|
||||
)
|
||||
|
||||
return token
|
||||
|
||||
async def _dual_engine_analyze(
|
||||
|
||||
Reference in New Issue
Block a user