本卡屬 FR-091(母卡 CM-1690),版面殘留回補。只動 jedi-integrity 一支,主專案不改(靠 re-export)。建議 model:Sonnet 5,effort:medium——搬檔+補 re-export+守衛,判斷點只有「哪個檔歸哪層」,卡上已分好。

問題是什麼(白話)

決策者 2026-09-13 打開 jedi-integrity 看到一片亂:jedi_integrity/ 底下 plugin/ 五檔是照標準拆好了,旁邊卻還有 12 支 .py 平鋪在頂層(config、context、forensic、lc_report、lockdown、manifest、ports、runtime_check、startup_gate、tamper_marker、termination、unlock),總共 2248 行;app/infra/ 各只有一支檔,沒有 domain/。這是 FR-064 當初寫的形狀,CM-1693 整理時只做了清註解、拆 plugin、logger、版面守衛,沒動這 12 支的位置。21 支套件裡只有它這樣(iam 另有一支 security_policy.py 平鋪,在 CM-1725 收)。

這支套件特殊在:沒有 route、啟動閘門在 create_app() 之前跑、DB 未開 DI 未 wire,所以 README 專門有一節「為什麼沒有 api 層」。但「沒有 api 層」不等於「不分層」,其他層的規則對它一樣適用。這次把 12 支歸位,對外 import 路徑一字不改。

首腦核對過的現況

怎麼做(一個 commit 搬完+一個 commit 守衛,或合一)

歸位表(首腦依 docstring 與 import 分的,runner 開檔確認,有異議先回寫再動):

domain/config.py         ← config.py        (IntegrityConfig 純參數值)
domain/context.py        ← context.py       (config+adapters 一束)
domain/ports.py          ← ports.py         (宿主要給的 port ABC)
domain/manifest.py       ← manifest.py      (manifest 載入/驗章/比對,純邏輯,hashlib+json)
domain/tamper_marker.py  ← tamper_marker.py (標記檔格式;若含 pathlib 寫檔則改放 infra/)
app/startup_gate.py      ← startup_gate.py  (啟動閘門流程編排)
app/runtime_check.py     ← runtime_check.py (抽查流程+埋點)
app/unlock.py            ← unlock.py        (token 核銷流程)
infra/lockdown.py        ← lockdown.py      (http.server 殼,碰網路)
infra/termination.py     ← termination.py   (os.kill/signal,碰 OS)
infra/forensic.py        ← forensic.py      (寫存證檔,碰檔案系統)
infra/lc_report.py       ← lc_report.py     (回報 License Center,碰網路)

要寫測試