From c60b7ce41633c8bf025d18717fbf6acdc88c9d4c Mon Sep 17 00:00:00 2001 From: Your Name Date: Tue, 30 Jun 2026 19:07:38 +0800 Subject: [PATCH] fix(cd): keep recovery evidence on controlled profile --- .gitea/workflows/cd.yaml | 13 +++++++++++++ docs/LOGBOOK.md | 15 +++++++++++++++ ops/runner/test_cd_controlled_runtime_profile.py | 8 ++++++++ 3 files changed, 36 insertions(+) diff --git a/.gitea/workflows/cd.yaml b/.gitea/workflows/cd.yaml index f1b852c23..c2b35325d 100644 --- a/.gitea/workflows/cd.yaml +++ b/.gitea/workflows/cd.yaml @@ -240,6 +240,10 @@ jobs: ;; docs/LOGBOOK.md) ;; + docs/runbooks/REBOOT-POST-START-QUICK-CHECK.md) + ;; + docs/workplans/2026-06-04-reboot-cold-start-backup-recovery-workplan.md) + ;; docs/schemas/product_awoooi_manifest_v1.schema.json) ;; docs/operations/product-awoooi-manifest-standard.snapshot.json) @@ -476,10 +480,14 @@ jobs: ;; ops/runner/verify-awoooi-non110-cd-closure.py) ;; + ops/monitoring/alerts-unified.yml) + ;; scripts/dev/awoooi-navigation-coverage-guard.py) ;; scripts/ci/wait-host-web-build-pressure.sh) ;; + scripts/ops/backup-health-textfile-exporter.py) + ;; scripts/reboot-recovery/dr-escrow-evidence-checklist.py) ;; scripts/reboot-recovery/post-reboot-owner-response-preflight.py) @@ -518,6 +526,8 @@ jobs: ;; scripts/reboot-recovery/tests/test_post_start_quick_check_contract.py) ;; + scripts/reboot-recovery/tests/test_reboot_p0_operational_contract.py) + ;; scripts/security/gitea-private-inventory-p0-scorecard.py) ;; scripts/security/gitea-authenticated-inventory-payload-validator.py) @@ -661,8 +671,10 @@ jobs: ../../scripts/reboot-recovery/dr-escrow-evidence-checklist.py \ ../../scripts/reboot-recovery/post-reboot-owner-response-preflight.py \ ../../scripts/reboot-recovery/reboot-auto-recovery-slo-scorecard.py \ + ../../scripts/ops/backup-health-textfile-exporter.py \ ../../scripts/security/gitea-private-inventory-p0-scorecard.py \ ../../scripts/security/gitea-authenticated-inventory-payload-validator.py + python3.11 -c "import yaml; yaml.safe_load(open('../../ops/monitoring/alerts-unified.yml')); print('alerts-unified YAML OK')" bash -n \ ../../scripts/reboot-recovery/install-reboot-auto-recovery-slo-110.sh \ ../../scripts/reboot-recovery/reboot-auto-recovery-host-probe.sh \ @@ -715,6 +727,7 @@ jobs: ../../scripts/reboot-recovery/tests/test_reboot_auto_recovery_slo_scorecard.py \ ../../scripts/reboot-recovery/tests/test_188_host_hygiene_checklist.py \ ../../scripts/reboot-recovery/tests/test_post_start_quick_check_contract.py \ + ../../scripts/reboot-recovery/tests/test_reboot_p0_operational_contract.py \ ../../scripts/security/tests/test_gitea_private_inventory_p0_scorecard.py \ ../../scripts/security/tests/test_gitea_authenticated_inventory_payload_validator.py \ -v --tb=short -x -p no:cacheprovider \ diff --git a/docs/LOGBOOK.md b/docs/LOGBOOK.md index a3444d42f..39afc7097 100644 --- a/docs/LOGBOOK.md +++ b/docs/LOGBOOK.md @@ -50365,3 +50365,18 @@ production browser smoke: **下一步**: - 先恢復 110 SSH read-only command path,才能驗證 Stock DB/schema、Gitea dump、110 backup completeness。 - 將 188 Gitea subtree backup metric 部署到 runtime textfile exporter 後,確認 `awoooi_backup_coverage_domain_fresh{host="188",domain="service"}` 能在 Gitea 子樹空目錄時告警。 + +## 2026-06-30 — 19:35 P0 recovery evidence CD controlled-runtime profile 修復 + +**完成內容**: +- 公開 Gitea readback 顯示 `#4035` / `4e909b211` 失敗,jobs log 不公開且 token required;未讀 secret、未用 Gitea API write、未 workflow_dispatch。 +- 定位可復現 source-side 風險:`docs/runbooks/REBOOT-POST-START-QUICK-CHECK.md`、reboot workplan、`ops/monitoring/alerts-unified.yml`、`scripts/ops/backup-health-textfile-exporter.py`、`scripts/reboot-recovery/tests/test_reboot_p0_operational_contract.py` 未列入 CD `controlled-runtime` whitelist,會讓 P0 recovery evidence 變更落入 full/B5 路徑。 +- 修正 `.gitea/workflows/cd.yaml`:上述 P0 recovery evidence / alert / exporter / contract test 改走 controlled-runtime;窄 profile 補 `alerts-unified.yml` YAML parse、backup exporter `py_compile`、reboot operational contract pytest。 +- 更新 `ops/runner/test_cd_controlled_runtime_profile.py`,鎖住這批路徑與 verifier,避免同類 P0 recovery evidence 再誤進 full/B5。 + +**本地驗證結果**: +- rebase 到 `c6c90e72f fix(api): redact autonomous runtime public payload terms` 後,`DATABASE_URL=postgresql+asyncpg://test:test@localhost:5432/test PYTHONPATH=apps/api python3.11 -m pytest ... -q`:`72 passed`。 +- `ruff check`、`py_compile`、`alerts-unified.yml` YAML parse、`guard-gitea-runner-pressure.py`、`check-gitea-step-env-secrets.js`、`git diff --check`:通過。 + +**下一步**: +- commit/push 後等待新的 Gitea CD run;deploy marker 更新後讀回 `delivery-closure-workbench`、`awoooi-priority-work-order-readback`、`stockplatform-public-api-controlled-recovery-preflight`。 diff --git a/ops/runner/test_cd_controlled_runtime_profile.py b/ops/runner/test_cd_controlled_runtime_profile.py index f6fd32a53..645c57036 100644 --- a/ops/runner/test_cd_controlled_runtime_profile.py +++ b/ops/runner/test_cd_controlled_runtime_profile.py @@ -355,6 +355,10 @@ def test_reboot_auto_recovery_slo_sources_stay_on_controlled_runtime_profile() - def test_post_start_recovery_verifiers_stay_on_controlled_runtime_profile() -> None: text = _workflow_text() expected_sources = [ + "docs/runbooks/REBOOT-POST-START-QUICK-CHECK.md)", + "docs/workplans/2026-06-04-reboot-cold-start-backup-recovery-workplan.md)", + "ops/monitoring/alerts-unified.yml)", + "scripts/ops/backup-health-textfile-exporter.py)", "scripts/reboot-recovery/post-start-quick-check.sh)", "scripts/reboot-recovery/188-host-hygiene-maintenance-checklist.sh)", "scripts/reboot-recovery/full-stack-cold-start-check.sh)", @@ -363,6 +367,9 @@ def test_post_start_recovery_verifiers_stay_on_controlled_runtime_profile() -> N "scripts/reboot-recovery/tests/test_188_host_hygiene_checklist.py)", "scripts/reboot-recovery/tests/test_post_start_quick_check_contract.py)", "scripts/reboot-recovery/tests/test_cold_start_monitor_bounded_probes.py)", + "scripts/reboot-recovery/tests/test_reboot_p0_operational_contract.py)", + "../../scripts/ops/backup-health-textfile-exporter.py", + "../../ops/monitoring/alerts-unified.yml", "../../scripts/reboot-recovery/post-start-quick-check.sh", "../../scripts/reboot-recovery/188-host-hygiene-maintenance-checklist.sh", "../../scripts/reboot-recovery/full-stack-cold-start-check.sh", @@ -371,6 +378,7 @@ def test_post_start_recovery_verifiers_stay_on_controlled_runtime_profile() -> N "../../scripts/reboot-recovery/tests/test_188_host_hygiene_checklist.py", "../../scripts/reboot-recovery/tests/test_post_start_quick_check_contract.py", "../../scripts/reboot-recovery/tests/test_cold_start_monitor_bounded_probes.py", + "../../scripts/reboot-recovery/tests/test_reboot_p0_operational_contract.py", ] for source in expected_sources: assert source in text