# RunBook: Phase E — SignOz Webhook Handler 生產部署 > **類型**: 操作型 RunBook > **優先級**: 🔴 P0 > **建立**: 2026-03-29 12:35 (台北) > **建立者**: Antigravity > **工時預估**: 1.5–2 小時 > **前置條件**: SignOz UI 可在 http://192.168.0.188:3301 正常訪問 --- ## 背景與現況 ### 🔍 精確現況診斷 ``` signoz_webhook.py → 完整實作 (363 行,含 4 步驟完整流程) main.py:419 → 已正確路由 include_router(signoz_webhook_v1.router) 端點:POST /api/v1/webhooks/signoz/alert ✅ 已可接收 問題:SignOz 告警規則未指向此 Webhook ``` **唯一阻塞點**:SignOz 告警規則 (`ops/signoz/alerting/rules.yaml`) 的 `webhook` 欄位尚未設定或未部署到 SignOz 主機。 ### 完整資料流 ``` SignOz 偵測到異常 (Error Rate / Latency / No Traces) ↓ SignOz Alert Manager 觸發告警 ↓ POST http://192.168.0.120:32334/api/v1/webhooks/signoz/alert ← 需要配置 ↓ process_signoz_alert() [Background Task] ↓ ├── AnomalyCounter 記錄頻率 (ADR-037) ✅ ├── IncidentService 建立事件 ✅ ├── ApprovalService 建立簽核 ✅ └── TelegramGateway 發送通知 ✅ ``` --- ## Step 1: 確認 API 端點可達 ```bash # 從 188 主機測試 SignOz Webhook 端點 curl -s http://192.168.0.120:32334/api/v1/webhooks/signoz/health # 預期:{"status": "ok", "service": "signoz-webhook", "timestamp": "..."} # 如端點不通,確認 Pod 狀態 kubectl get pod -n awoooi-prod -l app=awoooi-api ``` --- ## Step 2: 設定 SignOz 告警規則 ### 2.1 確認 ops/signoz/alerting/rules.yaml 已建立 ```bash # 確認檔案存在 ls /Users/ogt/awoooi/ops/signoz/alerting/ # 如不存在,從 IMPLEMENTATION_STEPS_REMAINING_PHASES.md 的 Phase E 代碼複製 ``` ### 2.2 部署告警規則到 SignOz 主機 ```bash # 登入 SignOz 主機 ssh root@192.168.0.188 # 確認 SignOz 告警配置目錄 docker inspect signoz-query-service | grep -A5 "Mounts" # 常見路徑:/opt/signoz/config/ 或 /data/signoz/ # 複製告警規則(從本機) # 先在本機執行: scp /Users/ogt/awoooi/ops/signoz/alerting/rules.yaml \ root@192.168.0.188:/opt/signoz/config/alerting/ # 在 188 主機重啟 SignOz Alert Manager(不重啟整個 SignOz) docker restart signoz-alert-manager 2>/dev/null || \ docker restart signoz # 若是單容器部署 ``` ### 2.3 透過 SignOz API 驗證規則載入 ```bash # 在 188 主機執行 curl -s http://localhost:3301/api/v3/alerts/rules | python3 -m json.tool | head -40 # 預期看到 APIHighErrorRate, APIHighLatencyP99 等規則名稱 ``` --- ## Step 3: 設定 SignOz Webhook Channel SignOz 告警通知支援 Webhook Channel,需要透過 SignOz Web UI 或 API 設定。 ### 3.1 透過 SignOz UI 設定(推薦) ``` 瀏覽器開啟:http://192.168.0.188:3301 路徑:Settings → Alert Channels → New Channel 類型:Webhook 名稱:AWOOOI-API URL:http://192.168.0.120:32334/api/v1/webhooks/signoz/alert Send resolved notifications:☑ (可選) ``` ### 3.2 透過 API 設定(腳本化) ```bash # 在 188 主機執行 curl -s -X POST http://localhost:3301/api/v1/channels \ -H "Content-Type: application/json" \ -d '{ "name": "AWOOOI-API", "type": "webhook", "data": { "webhook_url": "http://192.168.0.120:32334/api/v1/webhooks/signoz/alert" } }' # 預期返回 channel ID ``` --- ## Step 4: 建立測試告警規則 為了驗證整個鏈路,建立一個低閾值測試規則: ```bash # 在 188 主機的 SignOz 目錄建立測試規則 cat > /tmp/test-alert.yaml << 'EOF' groups: - name: e2e_test rules: - alert: AWOOOI_E2E_SMOKE_TEST expr: up{job="awoooi-api"} == 1 # 永遠觸發(API 存活時) for: 1m labels: severity: info source: signoz test: "true" annotations: summary: "E2E Smoke Test - 請忽略" description: "這是 AWOOOI 告警鏈路的自動測試" webhook: "http://192.168.0.120:32334/api/v1/webhooks/signoz/alert" EOF ``` --- ## Step 5: 端到端驗證 ### 5.1 手動觸發測試 ```bash # 直接向 AWOOOI API 發送模擬 SignOz 告警 curl -s -X POST http://192.168.0.120:32334/api/v1/webhooks/signoz/alert \ -H "Content-Type: application/json" \ -d '{ "alertname": "APIHighErrorRate", "status": "firing", "labels": { "alertname": "APIHighErrorRate", "severity": "critical", "service_name": "awoooi-api", "source": "signoz" }, "annotations": { "summary": "API 錯誤率 > 5%", "description": "服務 awoooi-api 錯誤率超標,這是一個測試告警" }, "startsAt": "2026-03-29T12:00:00Z" }' # 預期回應 # {"status": "ok", "processed": 1, "results": [{"status": "accepted", "alert_name": "APIHighErrorRate"}]} ``` ### 5.2 確認 Telegram 收到告警 ``` 預期在 Telegram Bot 中收到: ═══════════════════════════ 📊 SignOz: APIHighErrorRate ═══════════════════════════ 服務:awoooi-api 摘要:API 錯誤率 > 5% [ Y 確認 ] [ N 忽略 ] ``` ### 5.3 確認 API 日誌 ```bash kubectl logs -n awoooi-prod \ $(kubectl get pod -n awoooi-prod -l app=awoooi-api -o name | head -1) \ --tail=30 | grep -i signoz # 預期看到: # signoz_alert_received payload=... # signoz_anomaly_recorded alert_name=APIHighErrorRate # signoz_alert_processed alert_name=APIHighErrorRate incident_id=xxx # signoz_telegram_sent approval_id=xxx ``` --- ## 驗收標準 | 項目 | 通過條件 | |------|---------| | Webhook 端點可達 | `curl .../signoz/health` 返回 200 | | SignOz 規則載入 | `/api/v3/alerts/rules` 包含 `APIHighErrorRate` | | 手動測試正常 | 回應 `{"status": "ok"}` | | Telegram 通知 | 成功收到告警卡片 | | Incident 建立 | DB 中可查到 `source=signoz` 的 Incident | | Approval 建立 | `GET /api/v1/approvals` 顯示新 Approval | --- ## 常見問題排除 | 症狀 | 診斷 | 解法 | |------|------|------| | Webhook 404 | `curl .../signoz/health` | 確認主機是 32334 而非 8089 | | SignOz 規則不觸發 | SignOz UI → Alerts 頁 | 確認 Prometheus 端點可抓到 awoooi-api metrics | | Telegram 未收到 | 查 API 日誌 | 確認 `OPENCLAW_TG_BOT_TOKEN` Secret 已注入 | | Incident 建立失敗 | 查 API 日誌 `incident_creation_failed` | 確認 PostgreSQL 連線正常 |