@wooojin/forgen 0.3.1 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (125) hide show
  1. package/.claude-plugin/plugin.json +7 -2
  2. package/CHANGELOG.md +164 -0
  3. package/README.ja.md +90 -7
  4. package/README.ko.md +44 -1
  5. package/README.md +128 -9
  6. package/README.zh.md +90 -7
  7. package/dist/cli.js +140 -8
  8. package/dist/core/auto-compound-runner.js +16 -5
  9. package/dist/core/dashboard.js +11 -4
  10. package/dist/core/doctor.d.ts +6 -1
  11. package/dist/core/doctor.js +85 -11
  12. package/dist/core/global-config.d.ts +2 -2
  13. package/dist/core/global-config.js +6 -14
  14. package/dist/core/harness.d.ts +3 -5
  15. package/dist/core/harness.js +34 -338
  16. package/dist/core/inspect-cli.js +65 -5
  17. package/dist/core/installer.d.ts +10 -0
  18. package/dist/core/installer.js +185 -0
  19. package/dist/core/paths.d.ts +0 -34
  20. package/dist/core/paths.js +0 -35
  21. package/dist/core/settings-injector.d.ts +13 -0
  22. package/dist/core/settings-injector.js +167 -0
  23. package/dist/core/settings-lock.d.ts +35 -2
  24. package/dist/core/settings-lock.js +65 -7
  25. package/dist/core/spawn.js +100 -39
  26. package/dist/core/state-gc.d.ts +49 -0
  27. package/dist/core/state-gc.js +163 -0
  28. package/dist/core/stats-cli.d.ts +15 -0
  29. package/dist/core/stats-cli.js +143 -0
  30. package/dist/core/uninstall.d.ts +1 -0
  31. package/dist/core/uninstall.js +36 -5
  32. package/dist/core/v1-bootstrap.js +11 -3
  33. package/dist/engine/classify-enforce-cli.d.ts +8 -0
  34. package/dist/engine/classify-enforce-cli.js +61 -0
  35. package/dist/engine/compound-cli.d.ts +27 -2
  36. package/dist/engine/compound-cli.js +69 -16
  37. package/dist/engine/compound-export.d.ts +15 -0
  38. package/dist/engine/compound-export.js +32 -5
  39. package/dist/engine/compound-loop.js +3 -2
  40. package/dist/engine/enforce-classifier.d.ts +31 -0
  41. package/dist/engine/enforce-classifier.js +123 -0
  42. package/dist/engine/learn-cli.js +52 -0
  43. package/dist/engine/lifecycle/bypass-detector.d.ts +34 -0
  44. package/dist/engine/lifecycle/bypass-detector.js +82 -0
  45. package/dist/engine/lifecycle/lifecycle-cli.d.ts +7 -0
  46. package/dist/engine/lifecycle/lifecycle-cli.js +102 -0
  47. package/dist/engine/lifecycle/meta-cli.d.ts +4 -0
  48. package/dist/engine/lifecycle/meta-cli.js +7 -0
  49. package/dist/engine/lifecycle/meta-reclassifier.d.ts +78 -0
  50. package/dist/engine/lifecycle/meta-reclassifier.js +351 -0
  51. package/dist/engine/lifecycle/orchestrator.d.ts +32 -0
  52. package/dist/engine/lifecycle/orchestrator.js +131 -0
  53. package/dist/engine/lifecycle/signals.d.ts +30 -0
  54. package/dist/engine/lifecycle/signals.js +142 -0
  55. package/dist/engine/lifecycle/trigger-t1-correction.d.ts +23 -0
  56. package/dist/engine/lifecycle/trigger-t1-correction.js +78 -0
  57. package/dist/engine/lifecycle/trigger-t2-violation.d.ts +18 -0
  58. package/dist/engine/lifecycle/trigger-t2-violation.js +42 -0
  59. package/dist/engine/lifecycle/trigger-t3-bypass.d.ts +17 -0
  60. package/dist/engine/lifecycle/trigger-t3-bypass.js +39 -0
  61. package/dist/engine/lifecycle/trigger-t4-decay.d.ts +18 -0
  62. package/dist/engine/lifecycle/trigger-t4-decay.js +40 -0
  63. package/dist/engine/lifecycle/trigger-t5-conflict.d.ts +16 -0
  64. package/dist/engine/lifecycle/trigger-t5-conflict.js +78 -0
  65. package/dist/engine/lifecycle/types.d.ts +52 -0
  66. package/dist/engine/lifecycle/types.js +7 -0
  67. package/dist/engine/match-eval-log.js +45 -0
  68. package/dist/engine/rule-toggle-cli.d.ts +13 -0
  69. package/dist/engine/rule-toggle-cli.js +76 -0
  70. package/dist/engine/solution-format.d.ts +0 -2
  71. package/dist/engine/solution-format.js +0 -4
  72. package/dist/engine/solution-matcher.d.ts +8 -0
  73. package/dist/engine/solution-matcher.js +7 -4
  74. package/dist/engine/solution-outcomes.d.ts +4 -0
  75. package/dist/engine/solution-outcomes.js +174 -97
  76. package/dist/engine/solution-writer.d.ts +8 -5
  77. package/dist/engine/solution-writer.js +43 -19
  78. package/dist/fgx.js +9 -2
  79. package/dist/forge/cli.js +7 -7
  80. package/dist/forge/evidence-processor.js +10 -2
  81. package/dist/hooks/context-guard.js +86 -1
  82. package/dist/hooks/hook-config.d.ts +9 -1
  83. package/dist/hooks/hook-config.js +25 -3
  84. package/dist/hooks/internal/run-lifecycle-check.d.ts +2 -0
  85. package/dist/hooks/internal/run-lifecycle-check.js +32 -0
  86. package/dist/hooks/notepad-injector.js +6 -3
  87. package/dist/hooks/permission-handler.d.ts +10 -2
  88. package/dist/hooks/permission-handler.js +31 -12
  89. package/dist/hooks/post-tool-use.js +62 -0
  90. package/dist/hooks/pre-tool-use.js +67 -5
  91. package/dist/hooks/secret-filter.d.ts +10 -0
  92. package/dist/hooks/secret-filter.js +26 -0
  93. package/dist/hooks/session-recovery.js +15 -7
  94. package/dist/hooks/shared/atomic-write.d.ts +8 -1
  95. package/dist/hooks/shared/atomic-write.js +17 -3
  96. package/dist/hooks/shared/hook-response.d.ts +11 -2
  97. package/dist/hooks/shared/hook-response.js +20 -7
  98. package/dist/hooks/shared/hook-timing.js +10 -1
  99. package/dist/hooks/shared/safe-regex.d.ts +25 -0
  100. package/dist/hooks/shared/safe-regex.js +50 -0
  101. package/dist/hooks/shared/stop-triggers.d.ts +19 -0
  102. package/dist/hooks/shared/stop-triggers.js +19 -0
  103. package/dist/hooks/solution-injector.d.ts +21 -0
  104. package/dist/hooks/solution-injector.js +60 -1
  105. package/dist/hooks/stop-guard.d.ts +84 -0
  106. package/dist/hooks/stop-guard.js +482 -0
  107. package/dist/mcp/solution-reader.d.ts +2 -0
  108. package/dist/mcp/solution-reader.js +28 -1
  109. package/dist/mcp/tools.js +24 -4
  110. package/dist/preset/preset-manager.js +12 -2
  111. package/dist/store/evidence-store.d.ts +15 -0
  112. package/dist/store/evidence-store.js +55 -6
  113. package/dist/store/profile-store.d.ts +9 -0
  114. package/dist/store/profile-store.js +25 -4
  115. package/dist/store/rule-lifecycle.d.ts +23 -0
  116. package/dist/store/rule-lifecycle.js +63 -0
  117. package/dist/store/rule-store.d.ts +21 -0
  118. package/dist/store/rule-store.js +133 -13
  119. package/dist/store/types.d.ts +83 -0
  120. package/dist/store/types.js +7 -1
  121. package/hooks/hook-registry.json +1 -0
  122. package/hooks/hooks.json +6 -1
  123. package/package.json +10 -2
  124. package/plugin.json +7 -2
  125. package/scripts/postinstall.js +52 -5
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "$schema": "https://claude.ai/schemas/claude-plugin.json",
3
3
  "name": "forgen",
4
- "version": "5.1.2",
4
+ "version": "0.4.0",
5
5
  "description": "Claude Code harness — the more you use Claude, the better it gets",
6
6
  "author": {
7
7
  "name": "jang-ujin",
@@ -10,7 +10,12 @@
10
10
  "repository": "https://github.com/wooo-jin/forgen",
11
11
  "homepage": "https://github.com/wooo-jin/forgen",
12
12
  "license": "MIT",
13
- "keywords": ["claude-code", "harness", "personalization", "forge"],
13
+ "keywords": [
14
+ "claude-code",
15
+ "harness",
16
+ "personalization",
17
+ "forge"
18
+ ],
14
19
  "skills": "./skills/",
15
20
  "agents": "agents/",
16
21
  "statusLine": {
package/CHANGELOG.md CHANGED
@@ -5,6 +5,170 @@ All notable changes to forgen will be documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [0.4.0] - 2026-04-23
9
+
10
+ ### v0.4.0 — The Trust Layer
11
+
12
+ **When Claude says "done", forgen makes it prove it.** v0.4.0 adds turn-level self-verification at the Stop hook: Claude's completion claims get checked against rules you define, and blocks are fed back as `reason` that Claude reads and complies with on the next turn — **zero extra API calls**. Verified end-to-end on 10 scenarios at $1.74 total ([A1 spike report](docs/spike/mech-b-a1-verification-report.md)).
13
+
14
+ Built on top of the v0.3.x personalization core (4-axis profile + compound knowledge + rule rendering): the Trust Layer = 3-axis enforcement (Mech-A/B/C) + rule lifecycle (T1-T5 + Meta) + release self-gate. Interview rounds 9~10 mission "forgen 이 자기 규칙을 forgen 자신에게 강제 적용" achieved — this repo's own development was stopped mid-commit by its own L1 rule when the maintainer claimed "완결" without running Docker e2e (evidence preserved in `.forgen/state/enforcement/violations.jsonl`).
15
+
16
+ **ADR-001 — Mech-A/B/C 3축 강제 메커니즘** (Accepted)
17
+ - Mech-A (hook-BLOCK): 기계 판정 가능 규칙 — PreToolUse deny / Stop artifact_check.
18
+ - Mech-B (self-check prompt-inject): 자연어 판정 규칙 — Stop hook `decision:"block"` + `reason` 으로 Claude 자가점검 강제. **β1 ($0): 외부 LLM 호출 없음.**
19
+ - Mech-C (drift-measure): 정량 판정 불가 규칙 — 장기 편향만 측정.
20
+ - A1 검증 스파이크 10/10 PASS ($1.74, 3분): block 수용률 1.00, FP 0.00, hook p95 7ms, 추가 API 0.
21
+
22
+ **신규 타입** (`src/store/types.ts`):
23
+ - `EnforcementMech`, `HookPoint`, `VerifierSpec`, `EnforceSpec` — `Rule.enforce_via` 에 붙음 (optional, 기존 rule 하위 호환).
24
+ - `EnforceSpec.trigger_keywords_regex` / `trigger_exclude_regex` / `system_tag` — Stop hook 전용 발화 조건.
25
+ - `LifecyclePhase`, `LifecycleState`, `MetaPromotion` — `Rule.lifecycle` 에 붙음.
26
+
27
+ **신규 Hook**:
28
+ - `src/hooks/stop-guard.ts` — Stop hook. Production `rulesFromStore(loadActiveRules())` 로드, spike scenarios.json fallback. `last_assistant_message` 직접 read. stuck-loop guard (threshold 3 초과 시 force approve + drift 이벤트). `compoundCritical: true` (보호 hook).
29
+ - `src/hooks/shared/hook-response.ts::blockStop(reason, systemMessage?)` helper.
30
+
31
+ **ADR-002 — Rule Lifecycle Engine** (Accepted)
32
+ - T1 explicit_correction: `evidence-store.appendEvidence` → `detectT1` → rule retire/supersede/flag. axis + render_key 이중 매칭으로 FP 차단.
33
+ - T2 repeated_violation: 30d rolling window `violations_30d ≥ 3 AND rate > 0.3` → flag. 데이터 소스: `~/.forgen/state/enforcement/violations.jsonl` (stop-guard block 시 자동 append).
34
+ - T3 user_bypass: `post-tool-use` 에서 `bypass-detector.scanForBypass` → `recordBypass`. 7d `bypass_count ≥ 5` → suppress.
35
+ - T4 time_decay: `state-gc.runDailyT4Decay` — `forgen doctor --prune-state` 실행 시 90d 미주입 rule retire (별도 scheduler 없음; 사용자가 명시적으로 실행).
36
+ - T5 conflict_detected: `rule-store.appendRule` 에서 T5 감지, 양쪽 `conflict_refs` 기록.
37
+ - Meta 양방향: drift.jsonl 누적 → 강등 (A→B→C); rolling 20 injects + 0 violations → 승급 (B→A, C→B).
38
+ - Orchestrator `applyEvent` / `foldEvents` pure — rule 파일 쓰기는 호출자 책임.
39
+ - `src/store/rule-store.ts::markRulesInjected` — `v1-bootstrap` 이 renderRules 후 호출해 Meta 롤링 카운터를 채움.
40
+
41
+ **ADR-003 — Release Self-Gate** (Accepted)
42
+ - `.github/workflows/self-gate.yml` — push main / PR main / tag v* 에서 3-stage 검증.
43
+ - `scripts/self-gate.cjs` — 정적 스캔: mock-in-production, secrets-leak (AWS 공식 EXAMPLE fixture allow list), enforce_via-missing, release-artifact.
44
+ - `scripts/self-gate-runtime.cjs` — 6 hook 시나리오 smoke (완료 선언 block / retraction approve / shipped block / mock-context approve 등). 격리 HOME.
45
+ - `scripts/self-gate-release.cjs` — tag-only: version/tag match, CHANGELOG section, dist freshness, .forgen-release/e2e-report.json.
46
+
47
+ **신규 CLI**:
48
+ - `forgen rule <list|suppress|activate|scan|health-scan|classify>` — 규칙 관리 네임스페이스. 기존 플랫 커맨드(suppress-rule, activate-rule, lifecycle-scan, rule-meta-scan, classify-enforce)는 하위 호환 alias 로 유지.
49
+ - `forgen stats` — 한 화면 대시보드 (active rules, corrections, blocks/bypass/drift 7d, retired 7d, last extraction). 기존 jsonl 집계; 신규 telemetry 없음.
50
+ - `forgen inspect corrections` — `forgen inspect evidence` 의 사용자 친화 이름. evidence 는 alias 로 유지.
51
+ - `forgen last-block` — 가장 최근 block 이벤트 상세.
52
+
53
+ **내부 CLI (하위 호환, alias 로 유지)**:
54
+ - `forgen classify-enforce [--apply] [--force]` → `forgen rule classify`.
55
+ - `forgen rule-meta-scan [--apply]` → `forgen rule health-scan`.
56
+ - `forgen lifecycle-scan [--apply]` → `forgen rule scan`.
57
+
58
+ **Upgrade notes (v0.3.x → v0.4.0)**:
59
+ - 첫 `forgen` 실행 시 기존 rule 파일 (`~/.forgen/me/rules/*.json`) 에 `lifecycle` 블록이 자동 주입됩니다 (inject_count, phase='active' 등). 기존 필드는 보존됨.
60
+ - 프로젝트 로컬 `.forgen/rules/*.json` 이 자동 로드됩니다 (runtime 병합). 팀 dogfood 경로. 테스트/격리 필요 시 `FORGEN_DISABLE_PROJECT_RULES=1`.
61
+ - `FORGEN_USER_CONFIRMED=1` 으로 Mech-A PreToolUse 우회 시 violations.jsonl 에 `kind:'correction'` audit 엔트리 기록.
62
+
63
+ **운영 지표**:
64
+ - 전체 회귀 1973/1973 pass (169 files), TypeScript clean.
65
+ - forgen doctor 20/20 hooks active; legacy `~/.forgen/rules/` orphan 감지 추가.
66
+ - Self-gate 정적 ✓ + 런타임 7/7 (SG-ACK round-trip 포함); Docker e2e 77/77 (Phase 9 R9 전체 검증).
67
+ - `npm pack` tarball 539.3 kB, 332 파일, v0.4.0 메타데이터 확인.
68
+
69
+ **관측성**:
70
+ - `acknowledgments.jsonl` 신규 — Mech-B block → retract → pass 루프가 실제 작동한 세션 기록. `forgen stats` 의 `X% acknowledged` 라벨로 집계.
71
+
72
+ ## [0.3.2] - 2026-04-21
73
+
74
+ ### Security — Audit findings landed
75
+
76
+ Independent read-only audit (docs/claude-audit-brief.md) surfaced 10 structural
77
+ issues plus 2 follow-up findings. All 12 are fixed with invariant tests.
78
+
79
+ **P0 — data loss / code injection**
80
+ - **Settings parse-failure data loss** (#2, #10): `settings-injector.ts` and
81
+ `scripts/postinstall.js` no longer silently replace a malformed settings.json
82
+ with `{}`. New `readSettingsSafely()` preserves the corrupt original to
83
+ `settings.json.corrupt-<ts>` and throws; writers release the lock and abort.
84
+ postinstall settings + `~/.claude.json` now use tmp-file + rename atomic write.
85
+ - **Code injection via node -e** (#5): `session-recovery.ts` no longer
86
+ interpolates a user-supplied sessionId into a `-e` template literal. A
87
+ dedicated runner at `dist/hooks/internal/run-lifecycle-check.js` reads the id
88
+ from argv — no shell, no eval surface.
89
+ - **solution-outcomes race** (#9): all pending-state mutations are now serialised
90
+ under `withFileLockSync` + `atomicWriteJSON`. Concurrent inject / correction /
91
+ error hooks on the same session no longer lose or duplicate events.
92
+ - **Archive path traversal** (follow-up #A): `compound-export.importKnowledge`
93
+ rejects entries whose resolved destination sits outside ME_DIR, including
94
+ sibling-directory prefix collisions (e.g. `../me-evil/…`).
95
+
96
+ **P1 — lock semantics, trust, uninstall, injection precision**
97
+ - **Settings-lock live-holder handling** (#1): acquireLock now throws
98
+ `SettingsLockError` on live-PID timeout instead of overwriting the lock;
99
+ releaseLock verifies ownership before deleting.
100
+ - **Trust silent escalation** (#3): `preset-manager.computeEffectiveTrust`
101
+ returns a `Trust 상승` warning when runtime is more permissive than desired;
102
+ harness surfaces it to the user; fgx cautions `가드레일 우선`/`승인 완화`
103
+ profile users.
104
+ - **Install/uninstall symmetry** (#7): `uninstall` now strips `FORGEN_*` env
105
+ keys (previously only `COMPOUND_*`) and recognises `forgen me` (previously
106
+ only `forgen status`) as the forgen-owned statusLine.
107
+ - **Legacy profile guard** (#6): `loadProfile` runs `isV1Profile` and returns
108
+ null on legacy shapes so bootstrap re-runs cutover instead of typing stale
109
+ JSON as v1.
110
+ - **secret-filter vendor tokens** (follow-up #B): GitHub PATs (ghp_/gho_/
111
+ ghs_/ghu_/ghr_), Google API keys (AIza…), and Slack tokens (xox[abpors]-…)
112
+ are now detected.
113
+
114
+ **P2 — label truth, transcript attribution**
115
+ - **permission-handler labels** (#4): `approve()`/`approveWithWarning()` never
116
+ set `permissionDecision: 'allow'`; they are pass-through. Log and API labels
117
+ renamed to `safe-pass-through` / `autopilot-warn-pass-through` /
118
+ `autopilot-pass-through` / `pass-through` so audit trails match reality.
119
+ - **Transcript per-session attribution** (#8): `spawn.ts` snapshots existing
120
+ transcripts before launching claude and diffs after exit; concurrent sessions
121
+ in the same cwd no longer cross-attribute. Transcript reading switched to
122
+ streaming (`createReadStream` + `readline`).
123
+
124
+ ### Added — Data hygiene
125
+
126
+ Field audit on a ~2-week-old install found 10,802 files in `~/.forgen/state/`
127
+ across 12 filename prefixes, 4.3 MB `match-eval-log.jsonl`, and 80% of
128
+ error-attribution events concentrated on 3 solutions injected at relevance
129
+ 0.15–0.21.
130
+
131
+ - `forgen doctor --prune-state` (new `src/core/state-gc.ts`): removes session-
132
+ scoped files older than 7 days (checkpoint-, injection-cache-, modified-
133
+ files-, outcome-pending-, permissions-, skill-trigger-, tool-state-,
134
+ reminder-, context-, last-). Aggregate jsonl logs are preserved.
135
+ - `solution-outcomes.attributeError` gates: match_score ≥ 0.3,
136
+ injection-lag ≤ 5 min, top-3 by relevance. Prevents blanket blaming of
137
+ every injected solution when a tool fails.
138
+ - `solution-injector.MIN_INJECT_RELEVANCE = 0.3` + multi-tag precision gate
139
+ (`matchedIdentifiers ≥ 1 OR matchedTags ≥ 2`): the matcher remains
140
+ permissive for recall@5; only the injection step enforces the stricter
141
+ gate. Zero single-tag high-score injections observed in the field corpus
142
+ after landing.
143
+ - `match-eval-log.jsonl` size-based rotation at 10 MB (one generation
144
+ retained).
145
+
146
+ ### Fixed — e2e test isolation
147
+
148
+ Docker-spawned hooks in `tests/e2e/*.test.ts` were writing session state
149
+ (`e2e-tool-chain`, `chain5-test`, etc.) into the developer's real
150
+ `~/.forgen/state/`. Each e2e file now allocates a fresh `mkdtempSync` HOME
151
+ and injects it into the spawn env; `afterAll` cleans up. Likewise
152
+ `tests/hook-response-tracking.test.ts` now mocks `node:os` so the tracking
153
+ log never lands outside `/tmp/`.
154
+
155
+ ### Fixed — Stale Docker verify checks
156
+
157
+ `tests/e2e/docker/verify.sh` was asserting three skills that were deleted in
158
+ commit f534227 (v0.3 quality refactor). Result goes from 62/4/6 to 63/0/6
159
+ without touching runtime code.
160
+
161
+ ### Notes
162
+
163
+ - All fixes confirmed via invariant tests (1732/1732 pass across 143 files),
164
+ 7 real-world attack scenarios (injection, concurrent mutation, corrupt
165
+ settings, path traversal, prune, doctor smoke), and Linux-clean-environment
166
+ Docker verification.
167
+ - Upgrade path from 0.3.1 verified (profile + solutions + non-forgen settings
168
+ byte-identical after upgrade).
169
+ - Windows code paths exist but runtime validation is deferred to GH Actions
170
+ Windows runner — see P-D note in release audit.
171
+
8
172
  ## [0.3.1] - 2026-04-16
9
173
 
10
174
  ### Added — Self-Evolving Harness (inspired by Stanford meta-harness)
package/README.ja.md CHANGED
@@ -3,18 +3,18 @@
3
3
  </p>
4
4
 
5
5
  <p align="center">
6
- <strong>Claude Code パーソナライゼーション ハーネス。</strong><br/>
7
- <strong>使えば使うほど、あなたを理解する Claude。</strong>
6
+ <strong>Claude が「完了しました」と言ったら、forgen がそれを証明させる。</strong><br/>
7
+ ターンレベルの自己検証 + パーソナライズドルール、<strong>追加 API コスト $0</strong>。
8
8
  </p>
9
9
 
10
10
  <p align="center">
11
- <a href="https://www.npmjs.com/package//forgen"><img src="https://img.shields.io/npm/v//forgen.svg" alt="npm version"/></a>
11
+ <a href="https://www.npmjs.com/package/@wooojin/forgen"><img src="https://img.shields.io/npm/v/@wooojin/forgen.svg" alt="npm version"/></a>
12
12
  <a href="https://opensource.org/licenses/MIT"><img src="https://img.shields.io/badge/License-MIT-yellow.svg" alt="License: MIT"/></a>
13
13
  <a href="https://nodejs.org"><img src="https://img.shields.io/badge/node-%3E%3D20-brightgreen.svg" alt="Node.js >= 20"/></a>
14
14
  </p>
15
15
 
16
16
  <p align="center">
17
- <a href="#forgen-を使うと起こること">動作フロー</a> &middot;
17
+ <a href="#最初のブロック-30秒">最初のブロック</a> &middot;
18
18
  <a href="#クイックスタート">クイックスタート</a> &middot;
19
19
  <a href="#仕組み">仕組み</a> &middot;
20
20
  <a href="#4軸パーソナライゼーション">4軸</a> &middot;
@@ -32,8 +32,48 @@
32
32
 
33
33
  ---
34
34
 
35
+ ## 最初のブロック (30秒)
36
+
37
+ あなたは何度も騙されてきました。Claude は「テスト通過、実装完了」と言う — 実際に動かすと — 動かない。forgen はそのギャップを塞ぎます。
38
+
39
+ ```
40
+ You: 「ログインハンドラを実装してください。」
41
+ Claude: ...編集中...
42
+ Claude: "구현 완료했습니다。"
43
+
44
+ [forgen:stop-guard/L1-e2e-before-done]
45
+ Docker e2e 証拠 (~/.forgen/state/e2e-result.json, 1時間以内) がありません。
46
+ 実行してから再応答してください。
47
+
48
+ Claude: 「完了宣言を取り消します。証拠ファイルがありません。e2e を先に実行します...」
49
+ ...bash tests/e2e/docker/run-test.sh 実行...
50
+ 「63/63 通過。구현 완료했습니다。」
51
+
52
+ [forgen] ✓ approved
53
+ ```
54
+
55
+ **何が起きたか**: Claude の Stop フックが、あなたが定義したルール (`L1-e2e-before-done`) によってブロックされました。Claude はブロック `reason` を読み、早すぎた完了宣言を撤回し、証拠を生成して再提出しました。**追加 API コール 0** — Claude が元々生成する予定だった同じセッションのターン内で全て起きました。
56
+
57
+ これが **Mech-B セルフチェックプロンプトインジェクト** です。Claude Code の Stop フックが `decision: "block"` + `reason` を受け入れ、Claude が次のターンでその reason を入力として読むから成り立ちます。10 シナリオ $1.74 で end-to-end 検証済み ([A1 spike report](docs/spike/mech-b-a1-verification-report.md))。
58
+
59
+ 🎬 **動作を見る** (27秒):
60
+
61
+ ```bash
62
+ # 実際のフック・実際のルール・実際の block/approve サイクルをライブで
63
+ bash docs/demo/mech-b-demo.sh
64
+
65
+ # または録画済み asciinema キャストを再生
66
+ asciinema play docs/demo/mech-b-block-unblock.cast
67
+ ```
68
+
69
+ デモの「本物/シミュレーション」の区別は [`docs/demo/README.md`](docs/demo/README.md) を参照。
70
+
71
+ ---
72
+
35
73
  ## 2人の開発者。同じ Claude。まったく異なる振る舞い。
36
74
 
75
+ 上記の Trust Layer は柱の1つです。もう1つはパーソナライゼーション — 最初のブロック後に forgen を使い続ける理由です。
76
+
37
77
  開発者 A は慎重派です。Claude にすべてのテストを実行させ、理由を説明させ、現在のファイル以外を変更する前に必ず確認を求めます。
38
78
 
39
79
  開発者 B はスピード重視です。Claude に前提を置いて判断させ、関連ファイルも直接修正させ、結果を2行で報告させます。
@@ -57,7 +97,7 @@ forgen がこれを実現します。作業スタイルをプロファイリン
57
97
  ### 初回実行(1回のみ、約1分)
58
98
 
59
99
  ```bash
60
- npm install -g /forgen
100
+ npm install -g @wooojin/forgen
61
101
  forgen
62
102
  ```
63
103
 
@@ -117,7 +157,7 @@ Claude が `correction-record` MCP ツールを呼び出します。修正は、
117
157
 
118
158
  ```bash
119
159
  # 1. インストール
120
- npm install -g /forgen
160
+ npm install -g @wooojin/forgen
121
161
 
122
162
  # 2. 初回実行 — 4問オンボーディング(英語/韓国語選択)
123
163
  forgen
@@ -131,6 +171,35 @@ forgen
131
171
  - **Node.js** >= 20(SQLite セッション検索には >= 22 を推奨)
132
172
  - **Claude Code** インストール・認証済み(`npm i -g @anthropic-ai/claude-code`)
133
173
 
174
+ > **ベンダー依存:** forgen は Claude Code をラップします。Anthropic API または Claude Code の変更が動作に影響する可能性があります。Claude Code 1.0.x でテスト済みです。
175
+
176
+ ---
177
+
178
+ ## なぜ forgen か
179
+
180
+ | | Generic Claude Code | oh-my-claudecode | forgen |
181
+ |------------------------|:-------------------:|:----------------:|:---------------:|
182
+ | 全員に同じ | Yes | Yes | **No** |
183
+ | 修正から学習 | No | No | **Yes** |
184
+ | エビデンスベースのライフサイクル| No | No | **Yes** |
185
+ | 悪いパターンを自動リタイア| No | No | **Yes** |
186
+ | パーソナライズされたルール| No | No | **Yes** |
187
+ | ランタイム依存関係 | - | many | **3** |
188
+
189
+ ### forgen が向いているケース
190
+
191
+ **向いている場合:**
192
+ - 数週間かけて Claude があなたのパターンを学習する長期プロジェクト
193
+ - AI の振る舞いに強いこだわりがある開発者
194
+ - Compound 知識の恩恵を受ける繰り返しパターンがあるコードベース
195
+
196
+ **向いていない場合:**
197
+ - 使い捨てのスクリプトや一時的なプロトタイプ
198
+ - Claude Code がない環境
199
+ - すべてのメンバーに同じ AI 動作が必要なチーム(forgen は個人用であり、チーム向けではありません)
200
+
201
+ **forgen + oh-my-claudecode:** 一緒に使えます。OMC はオーケストレーション(エージェント、ワークフロー)を、forgen はパーソナライゼーション(プロファイル、学習)を担当します。[共存ガイド](docs/guides/with-omc.md) を参照してください。
202
+
134
203
  ---
135
204
 
136
205
  ## 仕組み
@@ -374,13 +443,27 @@ forgen forge --export # プロファイルをエクスポート
374
443
  ### 状態確認
375
444
 
376
445
  ```bash
446
+ forgen stats # 1画面 Trust Layer ダッシュボード (ルール・修正・block 7日)
447
+ forgen last-block # 直近のブロックイベント詳細
377
448
  forgen inspect profile # 4軸プロファイル + パック + ファセット
378
449
  forgen inspect rules # アクティブ/抑制されたルール
379
- forgen inspect evidence # 修正履歴
450
+ forgen inspect corrections # 修正履歴 (alias: evidence)
380
451
  forgen inspect session # 現在のセッション状態
452
+ forgen inspect violations # 最近のブロック記録 (--last N)
381
453
  forgen me # パーソナルダッシュボード(inspect profile のショートカット)
382
454
  ```
383
455
 
456
+ ### ルール管理
457
+
458
+ ```bash
459
+ forgen rule list # アクティブ + suppressed ルール一覧
460
+ forgen rule suppress <id> # ルールを無効化 (hard ルールは拒否)
461
+ forgen rule activate <id> # suppressed ルールを再アクティブ化
462
+ forgen rule scan [--apply] # ライフサイクルトリガー実行 (昇格/降格/引退)
463
+ forgen rule health-scan # drift → Mech 降格候補をスキャン
464
+ forgen rule classify # 既存ルールに enforce_via を自動提案
465
+ ```
466
+
384
467
  ### 知識管理
385
468
 
386
469
  ```bash
package/README.ko.md CHANGED
@@ -131,6 +131,35 @@ forgen
131
131
  - **Node.js** >= 20 (SQLite 세션 검색은 >= 22 권장)
132
132
  - **Claude Code** 설치 및 인증 (`npm i -g @anthropic-ai/claude-code`)
133
133
 
134
+ > **벤더 의존성:** forgen은 Claude Code를 래핑합니다. Anthropic API 또는 Claude Code 변경이 동작에 영향을 줄 수 있습니다. Claude Code 1.0.x 기준으로 테스트되었습니다.
135
+
136
+ ---
137
+
138
+ ## 왜 forgen인가
139
+
140
+ | | Generic Claude Code | oh-my-claudecode | forgen |
141
+ |------------------------|:-------------------:|:----------------:|:---------------:|
142
+ | 모두에게 동일 | Yes | Yes | **No** |
143
+ | 교정에서 학습 | No | No | **Yes** |
144
+ | Evidence 기반 라이프사이클| No | No | **Yes** |
145
+ | 나쁜 패턴 자동 은퇴 | No | No | **Yes** |
146
+ | 개인화된 규칙 | No | No | **Yes** |
147
+ | 런타임 의존성 | - | many | **3** |
148
+
149
+ ### 언제 사용하면 좋은가
150
+
151
+ **잘 맞는 경우:**
152
+ - 몇 주에 걸쳐 Claude가 패턴을 학습하는 장기 프로젝트
153
+ - AI 행동 방식에 강한 선호가 있는 개발자
154
+ - Compound 지식의 혜택을 받는 반복 패턴이 있는 코드베이스
155
+
156
+ **맞지 않는 경우:**
157
+ - 일회성 스크립트나 임시 프로토타입
158
+ - Claude Code가 없는 환경
159
+ - 모든 구성원이 동일한 AI 행동이 필요한 팀 (forgen은 개인용이지, 팀용이 아님)
160
+
161
+ **forgen + oh-my-claudecode:** 함께 사용할 수 있습니다. OMC는 오케스트레이션(에이전트, 워크플로우)을, forgen은 개인화(프로필, 학습)를 담당합니다. [공존 가이드](docs/guides/with-omc.md)를 참고하세요.
162
+
134
163
  ---
135
164
 
136
165
  ## 동작 방식
@@ -385,13 +414,27 @@ forgen forge --export # 프로필 내보내기
385
414
  ### 상태 확인
386
415
 
387
416
  ```bash
417
+ forgen stats # 한 화면 Trust Layer 대시보드 (규칙·교정·block 7일)
418
+ forgen last-block # 가장 최근 block 이벤트와 rule 상세
388
419
  forgen inspect profile # 4축 프로필 + 팩 + facet
389
420
  forgen inspect rules # 활성/비활성 규칙
390
- forgen inspect evidence # 교정 기록
421
+ forgen inspect corrections # 교정 기록 (alias: evidence)
391
422
  forgen inspect session # 현재 세션 상태
423
+ forgen inspect violations # 최근 block 기록 (--last N)
392
424
  forgen me # 개인 대시보드 (inspect profile 단축키)
393
425
  ```
394
426
 
427
+ ### 규칙 관리
428
+
429
+ ```bash
430
+ forgen rule list # 활성 + suppressed 규칙 목록
431
+ forgen rule suppress <id> # 규칙 비활성화 (hard 규칙은 거부)
432
+ forgen rule activate <id> # suppressed 규칙 재활성화
433
+ forgen rule scan [--apply] # 수명주기 트리거 실행 (승격/강등/은퇴)
434
+ forgen rule health-scan # drift → Mech 강등 후보 스캔
435
+ forgen rule classify # 레거시 규칙에 enforce_via 자동 제안
436
+ ```
437
+
395
438
  ### 지식 관리
396
439
 
397
440
  ```bash
package/README.md CHANGED
@@ -3,18 +3,18 @@
3
3
  </p>
4
4
 
5
5
  <p align="center">
6
- <strong>The Claude Code personalization harness.</strong><br/>
7
- <strong>The more you use Claude, the better it knows you.</strong>
6
+ <strong>When Claude says "done", forgen makes it prove it.</strong><br/>
7
+ Turn-level self-verification + personalized rules, at <strong>$0 extra API cost</strong>.
8
8
  </p>
9
9
 
10
10
  <p align="center">
11
- <a href="https://www.npmjs.com/package//forgen"><img src="https://img.shields.io/npm/v//forgen.svg" alt="npm version"/></a>
11
+ <a href="https://www.npmjs.com/package/@wooojin/forgen"><img src="https://img.shields.io/npm/v/@wooojin/forgen.svg" alt="npm version"/></a>
12
12
  <a href="https://opensource.org/licenses/MIT"><img src="https://img.shields.io/badge/License-MIT-yellow.svg" alt="License: MIT"/></a>
13
13
  <a href="https://nodejs.org"><img src="https://img.shields.io/badge/node-%3E%3D20-brightgreen.svg" alt="Node.js >= 20"/></a>
14
14
  </p>
15
15
 
16
16
  <p align="center">
17
- <a href="#what-happens-when-you-use-forgen">What Happens</a> &middot;
17
+ <a href="#the-first-block-30-seconds">First Block</a> &middot;
18
18
  <a href="#quick-start">Quick Start</a> &middot;
19
19
  <a href="#how-it-works">How It Works</a> &middot;
20
20
  <a href="#4-axis-personalization">4-Axis</a> &middot;
@@ -32,8 +32,48 @@
32
32
 
33
33
  ---
34
34
 
35
+ ## The first block (30 seconds)
36
+
37
+ You've been burned: Claude says "tests pass, implementation done" — you run it — it doesn't work. forgen closes that gap.
38
+
39
+ ```
40
+ You: "Implement the login handler."
41
+ Claude: ...makes edits...
42
+ Claude: "구현 완료했습니다."
43
+
44
+ [forgen:stop-guard/L1-e2e-before-done]
45
+ Docker e2e 증거(~/.forgen/state/e2e-result.json, 1시간 이내)가 없습니다.
46
+ 지금 실행 후 재응답하라.
47
+
48
+ Claude: "완료 선언을 취소합니다. 증거 파일이 없습니다. e2e 를 먼저 실행합니다..."
49
+ ...runs bash tests/e2e/docker/run-test.sh...
50
+ "63/63 pass. 구현 완료했습니다."
51
+
52
+ [forgen] ✓ approved
53
+ ```
54
+
55
+ **What just happened**: Claude's Stop hook was blocked by a rule you defined (`L1-e2e-before-done`). Claude read the block `reason`, retracted its premature claim, produced evidence, and re-submitted. **Zero extra API calls** — it all happened in the same session turn Claude was going to produce anyway.
56
+
57
+ This is **Mech-B self-check prompt-inject**. It works because Claude Code's Stop hook accepts `decision: "block"` + `reason`, and Claude in the next turn reads that reason as input. We verified it end-to-end on 10 scenarios at $1.74 total cost ([A1 spike report](docs/spike/mech-b-a1-verification-report.md)).
58
+
59
+ 🎬 **See it happen** (27 seconds):
60
+
61
+ ```bash
62
+ # Watch the full loop live — actual hook, actual rule, actual block/approve cycle
63
+ bash docs/demo/mech-b-demo.sh
64
+
65
+ # Or replay the pre-recorded asciinema cast
66
+ asciinema play docs/demo/mech-b-block-unblock.cast
67
+ ```
68
+
69
+ See [`docs/demo/README.md`](docs/demo/README.md) for what's real vs simulated in the demo.
70
+
71
+ ---
72
+
35
73
  ## Two developers. Same Claude. Completely different behavior.
36
74
 
75
+ The Trust Layer above is one pillar. The other is personalization — still the reason you'd keep forgen around after the first block.
76
+
37
77
  Developer A is careful. They want Claude to run all tests, explain reasoning, and ask before touching anything outside the current file.
38
78
 
39
79
  Developer B moves fast. They want Claude to make assumptions, fix related files automatically, and report results in two lines.
@@ -48,7 +88,7 @@ fix the session handler? Here's timeout not covered. Done."
48
88
  my analysis of each..."
49
89
  ```
50
90
 
51
- Forgen makes this happen. It profiles your work style, learns from your corrections, and renders personalized rules that Claude follows every session.
91
+ Forgen profiles your work style, learns from your corrections, and renders personalized rules that Claude follows every session.
52
92
 
53
93
  ---
54
94
 
@@ -109,7 +149,7 @@ Facets are micro-adjusted based on accumulated evidence. If your corrections con
109
149
 
110
150
  ### Next session
111
151
 
112
- Updated rules are rendered with your corrections included. Compound knowledge is searchable via MCP. Claude gets better at being *your* Claude.
152
+ Updated rules are rendered with your corrections included. Compound knowledge is searchable via MCP. Retrieval precision grows as your personal accumulation grows — the mechanism is in place from day 1 (starter-pack covers common dev queries on a fresh install), and the signal-to-noise ratio improves over roughly 2–4 weeks of real use as low-fitness solutions are auto-demoted and your specific patterns get promoted.
113
153
 
114
154
  ---
115
155
 
@@ -131,6 +171,35 @@ forgen
131
171
  - **Node.js** >= 20 (>= 22 recommended for SQLite session search)
132
172
  - **Claude Code** installed and authenticated (`npm i -g @anthropic-ai/claude-code`)
133
173
 
174
+ > **Vendor dependency:** Forgen wraps Claude Code. Anthropic API or Claude Code changes may affect behavior. Tested with Claude Code 1.0.x.
175
+
176
+ ---
177
+
178
+ ## Why forgen
179
+
180
+ | | Generic Claude Code | oh-my-claudecode | forgen |
181
+ |------------------------|:-------------------:|:----------------:|:---------------:|
182
+ | Same for everyone | Yes | Yes | **No** |
183
+ | Learns from corrections| No | No | **Yes** |
184
+ | Evidence-based lifecycle| No | No | **Yes** |
185
+ | Auto-retires bad patterns| No | No | **Yes** |
186
+ | Personalized rules | No | No | **Yes** |
187
+ | Runtime dependencies | - | many | **3** |
188
+
189
+ ### When to use forgen
190
+
191
+ **Good fit:**
192
+ - Long-running projects where Claude learns your patterns over weeks
193
+ - Developers with strong preferences about how AI should behave
194
+ - Codebases with recurring patterns that benefit from compound knowledge
195
+
196
+ **Not a fit:**
197
+ - One-off scripts or throwaway prototypes
198
+ - Environments without Claude Code
199
+ - Teams that need identical AI behavior for all members (forgen is personal, not team-wide)
200
+
201
+ **forgen + oh-my-claudecode:** They work together. OMC provides orchestration (agents, workflows); forgen provides personalization (profile, learning). See [Coexistence Guide](docs/guides/with-omc.md).
202
+
134
203
  ---
135
204
 
136
205
  ## How It Works
@@ -209,12 +278,16 @@ solution-injector matches: starter-error-handling-patterns (0.70)
209
278
  Claude sees: "Matched solutions: error-handling-patterns [pattern|0.70]
210
279
  Use try/catch with specific error types. Always log original error..."
211
280
 
212
- Claude writes better error handling code, informed by your accumulated patterns.
281
+ Claude has your accumulated patterns in context while drafting the response.
213
282
  ```
214
283
 
284
+ Precision gates (v0.3.2+): matches below relevance 0.3 or with only a single
285
+ common-word tag overlap are filtered before injection so Claude's context
286
+ doesn't get polluted by low-signal hits.
287
+
215
288
  ### 10 built-in skills
216
289
 
217
- Curated, compound-native skills. Each one integrates with accumulated knowledge — they get better every session.
290
+ Curated, compound-native skills. Each integrates with your accumulated knowledge — effectiveness compounds as your personal solution base grows.
218
291
 
219
292
  **Core chain** (build → learn):
220
293
 
@@ -418,13 +491,27 @@ forgen forge --export # Export profile
418
491
  ### Inspection
419
492
 
420
493
  ```bash
494
+ forgen stats # One-screen trust-layer dashboard (rules, corrections, blocks 7d)
495
+ forgen last-block # Most recent block event with rule detail
421
496
  forgen inspect profile # 4-axis profile with packs and facets
422
497
  forgen inspect rules # Active and suppressed rules
423
- forgen inspect evidence # Correction history
498
+ forgen inspect corrections # Correction history (alias: evidence)
424
499
  forgen inspect session # Current session state
500
+ forgen inspect violations # Recent block events (--last N)
425
501
  forgen me # Personal dashboard (shortcut for inspect profile)
426
502
  ```
427
503
 
504
+ ### Rule management
505
+
506
+ ```bash
507
+ forgen rule list # List active + suppressed rules
508
+ forgen rule suppress <id> # Disable a rule (hard rules refused)
509
+ forgen rule activate <id> # Re-activate a suppressed rule
510
+ forgen rule scan [--apply] # Run lifecycle triggers (promote/demote/retire)
511
+ forgen rule health-scan # Scan drift → Mech downgrade candidates
512
+ forgen rule classify # Propose enforce_via for legacy rules
513
+ ```
514
+
428
515
  ### Knowledge management
429
516
 
430
517
  ```bash
@@ -445,6 +532,7 @@ forgen skill list # List promoted skills
445
532
  ```bash
446
533
  forgen init # Initialize project
447
534
  forgen doctor # System diagnostics (10 categories + harness maturity)
535
+ forgen doctor --prune-state # Daily hygiene: state GC + T4 rule decay (90d idle → retire)
448
536
  forgen dashboard # Knowledge overview (6 sections)
449
537
  forgen config hooks # View hook status + context budget
450
538
  forgen config hooks --regenerate # Regenerate hooks
@@ -455,6 +543,37 @@ forgen notepad show # View session notepad
455
543
  forgen uninstall # Remove forgen cleanly
456
544
  ```
457
545
 
546
+ ### Rule lifecycle (v0.4.0, ADR-001/002)
547
+
548
+ ```bash
549
+ forgen classify-enforce # Preview enforce_via proposals for existing rules
550
+ forgen classify-enforce --apply # Save proposed enforce_via (skips already-set rules)
551
+ forgen classify-enforce --apply --force # Overwrite existing enforce_via
552
+ forgen rule-meta-scan # Preview Mech demotion candidates (drift.jsonl → A→B→C)
553
+ forgen rule-meta-scan --apply # Persist demotions + meta_promotions history
554
+ forgen lifecycle-scan # Preview T2~T5 + Meta (T1 fires inline on correction, not via CLI)
555
+ forgen lifecycle-scan --apply # Apply all lifecycle state transitions
556
+ ```
557
+
558
+ Rule enforcement is 3-axis (ADR-001):
559
+ - **Mech-A** (hook-BLOCK) — mechanical checks (`rm -rf`, artifact presence). Violation blocks immediately.
560
+ - **Mech-B** (self-check) — natural-language rules. Stop hook feeds self-check question back to Claude via `decision: "block"` + `reason`. Zero extra API cost.
561
+ - **Mech-C** (drift-measure) — long-term bias tracking only.
562
+
563
+ Rule lifecycle (ADR-002): rules auto-flag / suppress / retire / merge / supersede based on T1~T5 + Meta signals. Details in [docs/adr/ADR-002-rule-lifecycle-engine.md](docs/adr/ADR-002-rule-lifecycle-engine.md).
564
+
565
+ ### Release self-gate (v0.4.0, ADR-003)
566
+
567
+ Three CI gates prove forgen does not violate its own L1 rules before release:
568
+
569
+ ```bash
570
+ node scripts/self-gate.cjs # Static: mock-in-prod, secrets, enforce_via, release-artifact
571
+ node scripts/self-gate-runtime.cjs # Runtime smoke: 6 hook scenarios
572
+ node scripts/self-gate-release.cjs # Tag-only: version/tag/CHANGELOG/dist/e2e-report consistency
573
+ ```
574
+
575
+ Triggered by `.github/workflows/self-gate.yml` on push main / PR main / tag v*. Dogfood opt-in: see [.forgen/README.md](.forgen/README.md).
576
+
458
577
  ### MCP tools (available to Claude during sessions)
459
578
 
460
579
  | Tool | Purpose |