Files
awoooi/apps/api/tests/test_observability_contract_matrix.py
Your Name 4944d77093
All checks were successful
CD Pipeline / tests (push) Successful in 1m29s
Code Review / ai-code-review (push) Successful in 16s
CD Pipeline / build-and-deploy (push) Successful in 4m45s
CD Pipeline / post-deploy-checks (push) Successful in 1m31s
feat(governance): 新增監控合約降噪矩陣
2026-06-05 12:44:47 +08:00

294 lines
11 KiB
Python
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
from __future__ import annotations
import json
import pytest
from src.services.observability_contract_matrix import load_latest_observability_contract_matrix
def test_load_latest_observability_contract_matrix_reads_newest_file(tmp_path):
older = _snapshot(generated_at="2026-06-04T00:00:00+08:00", completion=40)
newer = _snapshot(generated_at="2026-06-05T00:00:00+08:00", completion=100)
(tmp_path / "observability_contract_matrix_2026-06-04.json").write_text(
json.dumps(older),
encoding="utf-8",
)
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(newer),
encoding="utf-8",
)
loaded = load_latest_observability_contract_matrix(tmp_path)
assert loaded["generated_at"] == "2026-06-05T00:00:00+08:00"
assert loaded["program_status"]["overall_completion_percent"] == 100
assert loaded["rollups"]["total_surfaces"] == 2
assert loaded["operation_boundaries"]["alertmanager_to_openclaw_allowed"] is False
def test_observability_contract_matrix_requires_read_only_mode(tmp_path):
snapshot = _snapshot()
snapshot["program_status"]["read_only_mode"] = False
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="read_only_mode"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_blocks_route_and_rule_mutations(tmp_path):
snapshot = _snapshot()
snapshot["operation_boundaries"]["prometheus_rule_write_allowed"] = True
snapshot["operation_boundaries"]["alertmanager_to_openclaw_allowed"] = True
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="operation boundaries"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_requires_rollup_consistency(tmp_path):
snapshot = _snapshot()
snapshot["rollups"]["surface_ids_requiring_action"] = []
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="surface_ids_requiring_action"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_requires_noise_candidates_to_be_proposal_only(tmp_path):
snapshot = _snapshot()
snapshot["noise_reduction_opportunities"][0]["proposal_only"] = False
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="proposal_only"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_requires_openclaw_receiver_denial(tmp_path):
snapshot = _snapshot()
snapshot["operator_contract"]["must_not_interpret_as"].remove(
"Alertmanager 指向 OpenClaw receiver 批准"
)
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="operator_contract"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_rejects_secret_payload_keys(tmp_path):
snapshot = _snapshot()
snapshot["latest_observations"][0]["webhook_secret"] = "redacted"
(tmp_path / "observability_contract_matrix_2026-06-05.json").write_text(
json.dumps(snapshot),
encoding="utf-8",
)
with pytest.raises(ValueError, match="forbidden secret payload key"):
load_latest_observability_contract_matrix(tmp_path)
def test_observability_contract_matrix_fails_when_missing(tmp_path):
with pytest.raises(FileNotFoundError):
load_latest_observability_contract_matrix(tmp_path)
def _snapshot(
*,
generated_at: str = "2026-06-05T00:00:00+08:00",
completion: int = 100,
) -> dict:
surfaces = [
_surface(
"prometheus_alert_rule_catalog",
"Prometheus 告警規則合約",
"prometheus_rules",
"action_required",
"proposal_only",
),
_surface(
"alertmanager_awoooi_route",
"Alertmanager → AWOOOI API 路由",
"alertmanager_route",
"verified",
"proposal_only",
),
]
opportunities = [
_opportunity("prometheus_noise_rule_tuning", "approval_required"),
_opportunity("alertmanager_grouping_inhibit_tuning", "approval_required"),
_opportunity("success_notification_quiet_policy", "preserved"),
]
gaps = [
{
"gap_id": "prometheus_alert_rule_catalog_seed",
"display_name": "Alert rule catalog seed 未正式產品化",
"status": "action_required",
"severity": "high",
"summary": "只讀矩陣已建立,尚未產生 catalog seed。",
"evidence_refs": ["docs/adr/ADR-090-monitoring-blindspot-governance.md"],
"next_action": "先產 proposal不改 rule。",
}
]
return {
"schema_version": "observability_contract_matrix_v1",
"generated_at": generated_at,
"program_status": {
"overall_completion_percent": completion,
"current_priority": "P1",
"current_task_id": "P1-003",
"next_task_id": "P1-004",
"read_only_mode": True,
},
"source_refs": ["docs/schemas/observability_contract_matrix_v1.schema.json"],
"rollups": {
"total_surfaces": len(surfaces),
"by_kind": _count_by(surfaces, "kind"),
"by_status": _count_by(surfaces, "status"),
"by_evidence_status": _count_by(surfaces, "evidence_status"),
"by_noise_policy_status": _count_by(surfaces, "noise_policy_status"),
"surface_ids_requiring_action": ["prometheus_alert_rule_catalog"],
"surface_ids_with_proposal_only_noise_policy": [
"alertmanager_awoooi_route",
"prometheus_alert_rule_catalog",
],
"noise_reduction_opportunities_total": len(opportunities),
"approval_required_opportunity_ids": [
"alertmanager_grouping_inhibit_tuning",
"prometheus_noise_rule_tuning",
],
"classification_gap_ids": ["prometheus_alert_rule_catalog_seed"],
"read_only_denials_total": 12,
},
"observability_surfaces": surfaces,
"noise_reduction_opportunities": opportunities,
"classification_gaps": gaps,
"latest_observations": [
{
"observation_id": "alertmanager_receiver_guard",
"status": "verified",
"summary": "Alertmanager 不得指向 OpenClaw。",
"evidence_refs": ["docs/HARD_RULES.md#alertmanager-routing"],
}
],
"operator_contract": {
"display_mode": "read_only_observability_contract_matrix",
"must_not_interpret_as": [
"Prometheus alert rule 修改批准",
"Alertmanager receiver / route 修改批准",
"Alertmanager 指向 OpenClaw receiver 批准",
"Silence 建立或維護窗口批准",
"Grafana dashboard 寫入批准",
"SigNoz / Sentry webhook 設定修改批准",
"Secret 已讀取或可輸出",
"Telegram 測試通知批准",
"deploy / reload / workflow 觸發批准",
"runtime execution 授權",
],
"secret_display_policy": "只顯示 redacted metadata。",
"alertmanager_route_policy": "OpenClaw 不接收 Alertmanager webhookreceiver 維持 AWOOOI API。",
"noise_reduction_policy": "只產生 proposal。",
"notification_policy": "成功不洗版。",
},
"operation_boundaries": {
"read_only_api_allowed": True,
"prometheus_rule_write_allowed": False,
"prometheus_reload_allowed": False,
"alertmanager_route_write_allowed": False,
"alertmanager_receiver_change_allowed": False,
"alertmanager_to_openclaw_allowed": False,
"silence_create_allowed": False,
"grafana_dashboard_write_allowed": False,
"grafana_api_write_allowed": False,
"signoz_query_mutation_allowed": False,
"signoz_webhook_change_allowed": False,
"sentry_webhook_change_allowed": False,
"otel_collector_deploy_allowed": False,
"event_exporter_restart_allowed": False,
"secret_read_allowed": False,
"secret_plaintext_allowed": False,
"notification_send_allowed": False,
"external_api_call_allowed": False,
"live_prometheus_query_allowed": False,
"workflow_trigger_allowed": False,
"deploy_trigger_allowed": False,
"reload_trigger_allowed": False,
"runtime_execution_allowed": False,
},
"approval_boundaries": {
"prometheus_rule_change_authorized": False,
"prometheus_reload_authorized": False,
"alertmanager_route_change_authorized": False,
"alertmanager_receiver_change_authorized": False,
"alertmanager_to_openclaw_authorized": False,
"silence_authorized": False,
"grafana_write_authorized": False,
"signoz_write_authorized": False,
"sentry_write_authorized": False,
"otel_deploy_authorized": False,
"event_exporter_restart_authorized": False,
"notification_send_authorized": False,
"external_call_authorized": False,
"secret_plaintext_allowed": False,
"workflow_trigger_authorized": False,
"deploy_reload_authorized": False,
"runtime_execution_authorized": False,
},
}
def _surface(
surface_id: str,
display_name: str,
kind: str,
status: str,
noise_policy_status: str,
) -> dict:
return {
"surface_id": surface_id,
"display_name": display_name,
"kind": kind,
"status": status,
"risk_level": "critical",
"evidence_status": "committed_manifest",
"noise_policy_status": noise_policy_status,
"coverage_contract": "只讀 committed evidence。",
"current_contract": "不得改 live 設定。",
"evidence_refs": ["docs/HARD_RULES.md"],
"next_action": "只產 proposal。",
}
def _opportunity(opportunity_id: str, status: str) -> dict:
return {
"opportunity_id": opportunity_id,
"display_name": opportunity_id,
"status": status,
"proposal_only": True,
"impact": "降噪提案。",
"evidence_refs": ["docs/HARD_RULES.md"],
"next_action": "人工批准前不執行。",
}
def _count_by(items: list[dict], key: str) -> dict[str, int]:
counts: dict[str, int] = {}
for item in items:
value = item[key]
counts[value] = counts.get(value, 0) + 1
return counts