STEP 1649 — pre-commit hook × checker arc 統合

2026-08-31 · arc 第 4 段 (enforcement layer) · STEP 1632/1635/1638 の 3 checker を commit 単位で 発火させる · STEP 1638 honest scope (iii) 「削除検出は verify を 誰かが 実行する に 依拠」 への 直接応答

目的

arc 3 段 (STEP 1632 spatial + STEP 1635 temporal + STEP 1638 irreversibility) は 「repo 常駐 の 部品」 として 実装された。 但し STEP 1638 の honest scope に 明示された 欠陥 = 「誰かが 手動で 実行しない 限り 誰も verdict を 見ない」。 本 STEP は 既存 scripts/git-hooks/pre-commit (3 section 実装済) に Section 4 を 追加し、 3 段を **commit 単位で 発火する 装置** に 昇格させる。

「repo 常駐 3 checker」 は 発火機構がないと 静的宣言のまま。 藤本さんの multi-tab 併走 で 別 tab が ledger を silently 破壊しても、 現状 では 誰かが 手動 verify を 走らせる まで 気付かない。 本 hook 統合で 「commit 時に 検出」 に 変わる。

Section 4 動作

Always: ledger verify (~1s)

if [ -f data/checker-ledger/entries.jsonl ]; then
  npx tsx scripts/checker/ledger-bootstrap.ts --verify
  # exit 1 → hook exit 1 + block message
  # exit 0 → 1 行 summary print + continue
fi

Conditional: arc test suites (staged file による)

staged file patterntrigger する test
scripts/checker/ledger*.ts or test/step1638-*.tstest:step1638 (73 test, ~2s)
scripts/checker/refactor-guard.ts or test/refactor-guards/ or test/step1635-*.tstest:step1635 (31 test, ~1s)
scripts/checker/arbitrariness-audit.ts or test/step1632-*.tstest:step1632 (28 test, ~1s)

Bypass

SKIP_CHECKER_VERIFY=1 git commit ...    # Section 4 のみ skip
SKIP_ALL_HOOKS=1 git commit ...          # 全 hook skip (既存)
git commit --no-verify                    # 全 hook skip (git native)

load-bearing 実測 evidence

Scenario A: tampered ledger → block

$ sed -i 's/"specDigest":"4e94/"specDigest":"deadbee/' data/checker-ledger/entries.jsonl
$ SKIP_LEAN_VERIFY=1 INBOX_PROTOCOL_BYPASS=1 bash scripts/git-hooks/pre-commit
[pre-commit] SKIP_LEAN_VERIFY=1 — skipping Lean verification

═══════════════════════════════════════════════════════════════
[pre-commit] Commit blocked: ledger verify FAILED (exit 1)

  chain: ok=false entries=2
    VIOLATION[hash-mismatch] seq=1: stored b7974b99b160… ≠ recomputed 0349e663fc50…
  bindings: ok=false total=1 intact=0 drifted=1 missing=0
    DRIFTED: harvest-lag-window-compared-does-not-follow-actual-retention …

This means one of:
  - the ledger chain has been tampered
  - a bound refactor-guard has been deleted (status = missing)
  - a bound refactor-guard has drifted structurally (status = drifted)

To bypass (defeats the purpose, use only for hook maintenance):
  SKIP_CHECKER_VERIFY=1 git commit ...
═══════════════════════════════════════════════════════════════

exit: 1

Scenario B: SKIP_CHECKER_VERIFY=1 bypass on same tampered state

$ SKIP_CHECKER_VERIFY=1 SKIP_LEAN_VERIFY=1 INBOX_PROTOCOL_BYPASS=1 bash scripts/git-hooks/pre-commit
[pre-commit] SKIP_LEAN_VERIFY=1 — skipping Lean verification
[pre-commit] SKIP_CHECKER_VERIFY=1 — skipping Section 4 (checker arc)

exit: 0

Scenario C: restored ledger → clean pass

$ SKIP_LEAN_VERIFY=1 INBOX_PROTOCOL_BYPASS=1 bash scripts/git-hooks/pre-commit
[pre-commit] SKIP_LEAN_VERIFY=1 — skipping Lean verification
[pre-commit] chain: ok=true entries=2 | bindings: ok=true total=1 intact=1 drifted=0 missing=0

exit: 0

3 scenario の 実測が Section 4 の 全 code path を cover。 block / bypass / pass の 3 判定が 期待通りに 動く 証拠。

test: 18/18 PASS (6 section)

test/step1649-pre-commit-checker-test.ts:
  Section 1: SKIP_CHECKER_VERIFY=1 bypass    (subprocess exit 0 + message check)
  Section 2: SKIP_ALL_HOOKS=1 regression      (Section 4 が 走らないこと の regression)
  Section 3: clean ledger, hook runs verify   (compact one-liner "chain: ok=true ... | bindings: ok=true ...")
  Section 4: tampered ledger detected         (temp tamper → verify exit 1 with hash-mismatch)
  Section 5: guard removed from registry      (temp REGISTRY empty → verify exit 1 with MISSING)
  Section 6: ledger-verify output shape       (line format stability for hook parsing)

Section 3 の bug fix (副産物)

実装過程で Section 3 (Lean 4 verify) の exit 0 が 2 箇所 (SKIP_LEAN_VERIFY 時 と 「no staged .lean file」 時) にあり、 Section 4 到達前に 抜けていた ことを 発見・修正。 section3_skipped=1 flag + if [ -n "$staged_lean" ] wrap で fall-through に 変更、 「Section 3 を skip しても Section 4 は 走る」 不変条件を 実装。

arc 4 段 完結の 集約

STEP部品次元testhook 統合
1632arbitrariness_auditspatial28conditional (staged file 時)
1635refactor-guardtemporal31conditional (staged file 時)
1638hash-chained ledgerirreversibility73always (~1s)
1649hook 統合enforcement18

arc 累計 test 150/150 PASS。 「保証は 外部からしか 来ない」 の 3 checker + 「commit 単位で 発火」 の enforcement layer で、 4 部品 が operational に 揃った。

Honest scope:

次段 candidate (第 5 段以降、 藤本さん go 待ち)

  1. git commit hash を ledger に anchor: kind:"git-commit-anchor" entry で "at commit ABC, ledger head was hash X" を post-commit で 記録。 外部 API 不要、 git 自体が 外部 anchor。 --no-verify の 抜け穴も 事後検出可能。
  2. GitHub Actions で checker:ledger-verify: local hook を 迂回した push を CI 側で catch。 pre-commit と 二重 wall。
  3. bypass log 監視: SKIP_CHECKER_VERIFY=1 使用の 累計 記録 → 「なぜ bypass したか」 の rationale trail。

参照

Commit: 別 push · Mirror force-track · STEP 1554 atomic-commit dogfood