fix(happy-path): Happy Path 全境加固 — INVALID_TARGET + critical NO_ACTION + 空指令攔截
Some checks failed
CD Pipeline / build-and-deploy (push) Has been cancelled

問題 1 (P0) — deployment/unknown 無效重啟:
- alert_rule_engine: 追蹤 _invalid_target flag,回傳 blocked_reason="INVALID_TARGET-..."
- decision_manager: auto_execute 路徑偵測 INVALID_TARGET → 提早返回 + TYPE-4 人工確認
- auto_approve: 新增條件 1c — action 為空字串直接拒絕,防止誤報「即將執行」

問題 2 (P1) — critical+NO_ACTION 靜默:
- decision_manager: blocked_reason 感知層重構
  ① INVALID_TARGET → TYPE-4
  ② NO_ACTION + critical → TYPE-4(升級,SRE 不可錯過)
  ③ NO_ACTION + 非 critical → TYPE-1(維持純資訊卡)

問題 3 (P1) — 規則匹配信心黑洞:
- auto_approve 條件 1c 確保空 action 不通過 auto-approve
  即便 is_rule_based=True 也無法在無指令時自動執行

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
OG T
2026-04-16 22:57:50 +08:00
parent 0077ff9758
commit 83ab5e32d7
3 changed files with 56 additions and 7 deletions

View File

@@ -372,6 +372,7 @@ def match_rule(alert_context: dict) -> dict[str, Any] | None:
# GAP-A4 (2026-04-14 Claude Sonnet 4.6): 後置驗證 — 垃圾 target 丟棄 command
# 避免 `kubectl rollout restart deployment unknown/HostHighCpuLoad/...` 這類無效指令
# 清空 kubectl_command 讓 decision_manager 降級給 LLM 處理
_invalid_target = False
if kubectl_command and _is_bad_target(vars["target"], alertname):
logger.warning(
"rule_kubectl_command_discarded_bad_target",
@@ -382,6 +383,7 @@ def match_rule(alert_context: dict) -> dict[str, Any] | None:
original_command=kubectl_command[:120],
)
kubectl_command = ""
_invalid_target = True
# 還有 {var} 殘留 → 模板變數未被 _fill 填滿(可能 vars 缺少對應 key
if kubectl_command and ("{" in kubectl_command or "}" in kubectl_command):
@@ -391,6 +393,15 @@ def match_rule(alert_context: dict) -> dict[str, Any] | None:
command=kubectl_command[:120],
)
kubectl_command = ""
_invalid_target = True
# 2026-04-16 ogt + Claude Sonnet 4.6: blocked_reason 讓 decision_manager 感知 target 失敗
# 根因rule engine 清空 kubectl_command 但不告訴下游原因 → decision_manager 繼續嘗試執行
# 修復:設定 blocked_reason="INVALID_TARGET - ..." 讓 auto_execute 路徑提早返回 + TYPE-4
_blocked_reason_out = (
f"INVALID_TARGET - target='{vars['target']}' 未解析為有效 Deployment需 SRE 人工確認"
if _invalid_target else ""
)
return {
"rule_id": matched_rule["id"],
@@ -416,6 +427,7 @@ def match_rule(alert_context: dict) -> dict[str, Any] | None:
"confidence": 0.0, # 🔴 規則匹配固定 0.0,禁止偽造
"affected_services": [vars["target"]],
"signoz_correlation": "",
"blocked_reason": _blocked_reason_out, # "" 正常 | "INVALID_TARGET - ..." 目標解析失敗
}