SUMMARY — 標記審閱(控制項 / AO sign-off)在 FR-040 失效修復

日期:2026-06-21 / branch FR-040-AP-improvement(BE + FE 皆未 push) 狀態:BE py_compile 過;user 手測 AO 標記 OK;控制項 FE 改動待手測。BE 需重啟、FE 重整頁面。

§1

Commits

Repo Commit 內容
compliance-manager-be a16a1953 review resolve 改走 living SSP(含 changelog)
compliance-manager-fe 6537e3c ctrlStatusFromAos 狀態/進度同源

兩 repo 各自只 commit 本 arc 檔案;working tree 仍夾其他 session WIP(BE api/project/*poam_app_service.pygrc_error_code.py;FE i18n + RoundApAuthoringView.vueRoundPoamView.vue),未動。

§2

問題與根因(三層)

  1. stg 500_resolve_control_idsLEFT JOIN compliance.project_assessment_plan_mapping 反查 project_id;該表 v1 遺留、v2 無寫入點,stg 0 筆 → project_id NULL → insert ReviewMark(NOT NULL)撞 IntegrityError。dev 留有 191 筆 v1 遺產才偶然能用。
  2. localhost 404 — 改 AP 鏈仍失敗:FR-040 規劃階段 round 無 AP(assessment_plan_id/ssp_id 皆 NULL,AP 待 launch_audit 才生),FE round 模式把 round uid 放進 /ap/<ap_uid> 段。
  3. 控制項按不下(FE)ctrlStatusFromAos summary 分支讀 total_tasks/completed_tasks 忽略 jobs,僅有 jobs 時算 total=0 → not_started;進度條讀 jobs → 100%。徽章/進度矛盾,gate 看徽章 → 鎖死。
§3

修法

  • BE:resolve 改與 get_ap_dashboard / control-tree 同源 —— projects.uid → project_extensions.living_ssp_id → ssp.import_profile_id → profile_imports.source_catalog_id → catalog_controlsproject_uid 一路串到 repo;不再依賴 AP / v1 mapping。
  • FEctrlStatusFromAos 拿掉忽略 jobs 的 fallback,一律走 jobs(原 detail 分支邏輯),狀態與進度同源。
§4

驗證

失敗請求(project 6d686f15、control IA.L1-3.5.1、AO IA.L1-3.5.1_obj.1)在 dev 跑新 query:project_id=282 / control_db_id=2844 / group_db_id=1009 / ao_id=14473,全非 NULL。

§5

已更新橫向文件

  • ✓ changelog docs/changelog/2026-06-21-fix-grc-review-mark-v2-living-ssp.md
  • ✓ Notion 任務(新建,狀態 Done)https://app.notion.com/p/386346da4cd08164a406d08116f1864f
  • ✓ memory feedback feedback_grc_v2_readers_resolve_via_living_ssp.md + feedback_fe_status_progress_same_source.md
  • ✓ 本 SUMMARY
§6

Follow-up

  • v1 遺留表 compliance.project_assessment_plan_mapping:review 已不依賴它,是否仍有其他 reader、可否退役 → 另案盤點(DROP 前走安全四查)。
  • 部署:BE 需重啟;兩 repo 未 push(等 user 指示)。
  • 對話紀錄歸檔:本次未做(user 未要求匯出對話);需要時 scripts/extract_claude_sessions.py --ts-prefix