@wooojin/forgen 0.4.4 → 0.4.5
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.
- package/.claude-plugin/plugin.json +1 -1
- package/CHANGELOG.md +136 -4
- package/README.md +13 -0
- package/assets/claude/commands/forge-loop.md +62 -2
- package/dist/cli.js +8 -0
- package/dist/core/settings-injector.js +8 -2
- package/dist/core/statusline-cli.d.ts +13 -0
- package/dist/core/statusline-cli.js +150 -0
- package/dist/hooks/hook-registry.js +9 -4
- package/dist/host/install-claude.js +34 -3
- package/package.json +1 -1
- package/plugin.json +1 -1
- package/scripts/postinstall.js +61 -6
- package/skills/architecture-decision/SKILL.md +21 -0
- package/skills/calibrate/SKILL.md +21 -0
- package/skills/code-review/SKILL.md +21 -0
- package/skills/compound/SKILL.md +21 -0
- package/skills/deep-interview/SKILL.md +21 -0
- package/skills/docker/SKILL.md +21 -0
- package/skills/forge-loop/SKILL.md +76 -1
- package/skills/learn/SKILL.md +21 -0
- package/skills/retro/SKILL.md +21 -0
- package/skills/ship/SKILL.md +21 -0
package/CHANGELOG.md
CHANGED
|
@@ -7,17 +7,149 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
### Fixed — forgen-eval testbed 측정 결함 (ADR-007)
|
|
11
|
+
|
|
12
|
+
`forgen-eval` ψ-stat 측정의 두 구조적 결함 식별 + 수정. 본 fix 이전 모든
|
|
13
|
+
ψ 측정 보고는 "ADR-007 이전 testbed 결함 위에서 산출됨" disclaimer 적용.
|
|
14
|
+
**v0.4.4 release note 의 mean ψ=+0.098 master gate PASS 도 본 disclaimer 대상**
|
|
15
|
+
(haiku judge + 결함 arm + 결함 mem 위 측정).
|
|
16
|
+
|
|
17
|
+
- **[testbed-P0] ForgenPlusMemArm single-session 결합** (`commit 25c8ac0`)
|
|
18
|
+
- 이전 구현은 forgen-only LLM 세션과 mem-only LLM 세션을 *각각* 돌리고
|
|
19
|
+
forgen 응답만 채택 — Driver 가 `qwen2.5:14b @ temp=0.3` 비결정 호출이라
|
|
20
|
+
`full.W − forgenOnly.W` 가 LLM stochastic noise 로 양/음 ±0.3 흔들림.
|
|
21
|
+
ψ 가 forgen+mem coexistence 신호 대신 LLM 분산을 측정.
|
|
22
|
+
- 한 LLM 세션 안에서 forgen UPS rule + claude-mem recall 을 둘 다 system
|
|
23
|
+
message 로 주입한 뒤 한 번 chat → forgen Stop guard 평가 구조로 재작성.
|
|
24
|
+
|
|
25
|
+
- **[testbed-P0] claude-mem 콘텐츠 직접 fetch** (`commit d65b4a4`)
|
|
26
|
+
- 이전 mem recall 은 `claude-mem search` CLI 출력 (검색 결과 *테이블* —
|
|
27
|
+
세션 ID + 제목만) 을 그대로 inject. LLM 컨텍스트로는 사실상 메타-noise
|
|
28
|
+
이고, 응답을 verbose / cautious / "context 더 주세요" 쪽으로 shift 시켜
|
|
29
|
+
sonnet judge 의 actionable advice 점수를 깎았음.
|
|
30
|
+
- 신규 `claudeMemRecallActual()` helper — 검색 후 ID 파싱 →
|
|
31
|
+
`~/.claude-mem/claude-mem.db` 의 `observations.narrative` /
|
|
32
|
+
`session_summaries.learned` 직접 조회 → 상위 N hit 의 실제 콘텐츠 inject
|
|
33
|
+
(`[#ID]\n<content>` 포맷). DB 미설치 환경에서 graceful no-op.
|
|
34
|
+
|
|
35
|
+
- **신규 분석 도구**: `src/runners/probe-mem-inject.ts` — judge 호출 없이
|
|
36
|
+
ForgenOnly + Full arm inject 텍스트와 응답을 콘솔에 덤프하는 정성 probe.
|
|
37
|
+
cross-talk 가설 검증에 사용.
|
|
38
|
+
|
|
39
|
+
- **신규 ADR**: `docs/adr/ADR-007-testbed-arm-isolation.md` — 두 결함의 발견
|
|
40
|
+
경위, 영향 받은 측정 목록, 재측정 계획, 회귀 가드 명시. 후속 정성 분석
|
|
41
|
+
(E, 2026-05-08) 으로 cross-talk 가설보다 LLM stochasticity (qwen2.5:14b @
|
|
42
|
+
temp=0.3 base error rate × 더 긴 context surface) 가 음수 ψ 의 더 강한 설명
|
|
43
|
+
임을 확인 — 다음 측정의 전제조건으로 Driver determinism (temp=0 + seed) 또는
|
|
44
|
+
더 강한 driver 권고.
|
|
45
|
+
|
|
46
|
+
- **재측정 결과 (track-mem-fix N=10 sonnet, 2026-05-08)**: 양쪽 fix 적용 후
|
|
47
|
+
mean ψ = −0.080, 95% CI [−0.161, −0.000], gate FAIL (음수 시그널). 7 음수 /
|
|
48
|
+
3 양수. v0.4.4 release note 의 mean ψ=+0.098 PASS 는 broken testbed 의
|
|
49
|
+
artifact 였음이 더 강하게 확정됨.
|
|
50
|
+
|
|
51
|
+
### Changed — driver 를 claude-cli / codex-cli 로 통일 (commit 62600ec, 11b897a)
|
|
52
|
+
|
|
53
|
+
testbed driver 가 Ollama qwen2.5:14b 로 남아 judge stack (claude-cli +
|
|
54
|
+
codex-cli) 과 불일치 + qwen base error rate (~30-50%) 가 noise 의 주 원인 이었던
|
|
55
|
+
문제를 production 시나리오 (forgen 이 personalize 하는 LLM = Claude 또는 Codex)
|
|
56
|
+
와 일치하는 driver 로 교체.
|
|
57
|
+
|
|
58
|
+
**측정 비교 (N=10 sonnet judge, 2026-05-11 ~ 12)**:
|
|
59
|
+
|
|
60
|
+
| Driver | N eff | mean ψ | CI | mean δ(forgenOnly−vanilla) | 양수 δ | κ γ |
|
|
61
|
+
|---|---|---|---|---|---|---|
|
|
62
|
+
| qwen mem-fix (이전) | 10 | −0.080 | [−0.161, −0.000] | (n/a) | — | (n/a) |
|
|
63
|
+
| claude (older fixes) | 10 | +0.020 | [−0.133, +0.158] | +0.046 | 7/10 | (n/a) |
|
|
64
|
+
| codex (all fixes) | 10 | +0.024 | [−0.029, +0.094] | +0.120 | 8/10 | 0.323 |
|
|
65
|
+
| claude (all fixes, rate-limit cut) | 9 | −0.013 | [−0.083, +0.039] | +0.156 | 8/9 | 0.429 |
|
|
66
|
+
| claude (retry+sequential N=20) | 20 | +0.016 | [−0.012, +0.047] | +0.096 | 14/20 | 0.583 |
|
|
67
|
+
| codex (retry+sequential N=20) | 20 | +0.013 | [−0.029, +0.055] | +0.133 | 19/20 | 0.048 |
|
|
68
|
+
| **claude (judge retry N=33)** | **33** | **−0.005** | **[−0.036, +0.029]** | **+0.125** | **30/33 (91%)** | **0.474** |
|
|
69
|
+
| **codex (judge retry N=33)** | **33** | **−0.021** | **[−0.068, +0.024]** | **+0.176** | **32/33 (97%)** | **0.263** |
|
|
70
|
+
| **POOLED N=66 — 학술 증명** | **66** | **−0.013** | — | **+0.151** | **62/66 (93.9%) — p=1×10⁻¹⁴** | — |
|
|
71
|
+
|
|
72
|
+
**핵심 발견**:
|
|
73
|
+
- ψ (forgen+mem coexistence) 는 양 driver 모두 noise 영역 — 부호가 driver 별로
|
|
74
|
+
갈리고 CI 가 0 가로지름. **forgen+mem 결합 효과는 통계적으로 측정 불가능.**
|
|
75
|
+
- δ (forgenOnly−vanilla) 는 **양 driver 일관 양수**, 다수 케이스 일관 — codex
|
|
76
|
+
driver 에서 +0.144 W. **forgen 단독 효과는 robust 하게 양수.**
|
|
77
|
+
- **셀링 메트릭 변경**: ψ 가 아닌 **δ (forgen vs vanilla)** 가 진짜 셀링
|
|
78
|
+
포인트. v0.4.4 의 ψ master gate PASS 주장 대신 v0.4.5 부터는 δ 중심 메시지.
|
|
79
|
+
|
|
80
|
+
**알려진 limitation**:
|
|
81
|
+
- ~~codex driver 1MB input 한계~~ ✓ FIXED (commit 1362d59 history cap 16K)
|
|
82
|
+
- ~~codex judge spawn E2BIG~~ ✓ FIXED (commit e42bff6 judge stdin pipe + 5c8dce8
|
|
83
|
+
material cap 32K). fallback 2.5: 56 → 3 (95% 감소).
|
|
84
|
+
- ~~claude CLI subscription rate-limit~~ ✓ FIXED commit 7b333b2 (driver retry +
|
|
85
|
+
exponential backoff). claude retry+sequential N=20 측정에서 retry 0회 발동
|
|
86
|
+
(sequential 만으로 충분), N=20 effective 회복.
|
|
87
|
+
|
|
88
|
+
### Fixed — Node 20.x 환경 호환성 (P0/P1)
|
|
89
|
+
|
|
90
|
+
`npm i -g @wooojin/forgen` 이후 "각종 훅이 에러난다"는 사용자 보고에 대응한 환경
|
|
91
|
+
호환성 일괄 강화. 보고 환경: M2 MacBook + Node 20.x.
|
|
92
|
+
|
|
93
|
+
- **[P0] hook-registry.ts import attributes 호환성** (`src/hooks/hook-registry.ts:56`)
|
|
94
|
+
- `import ... with { type: 'json' }` (Node 20.10+ 만 파싱 가능) → `JSON.parse(readFileSync(...))`
|
|
95
|
+
로 교체. Node 20.0–20.9 에서 모든 훅(23개)이 SyntaxError 로 깨지던 회귀를
|
|
96
|
+
제거. 빌드 산출물에 import attributes 가 재유입되는 것을 막는 정적 검증 테스트
|
|
97
|
+
`tests/hook-registry-portability.test.ts` 추가.
|
|
98
|
+
- 영향 범위: hook-config 를 거쳐 모든 PreToolUse / PostToolUse / Stop / SessionStart
|
|
99
|
+
/ UserPromptSubmit 훅이 Node 20.0–20.9 사용자 환경에서 동작하지 않던 상태에서
|
|
100
|
+
회복.
|
|
101
|
+
|
|
102
|
+
- **[P1] postinstall self-check** (`scripts/postinstall.js`)
|
|
103
|
+
- 설치 마지막 단계에서 `dist/hooks/hook-registry.js` 를 dynamic import 로 로드하고,
|
|
104
|
+
`HOOK_REGISTRY` 가 비어있지 않은지 확인. 실패 시 stderr 로 Node 버전과 원인을
|
|
105
|
+
명시해 사용자가 "왜 훅이 안 도는지" 를 install 시점에 즉시 알 수 있게 함
|
|
106
|
+
(npm install 자체는 깨뜨리지 않음).
|
|
107
|
+
|
|
108
|
+
- **[P1] install-claude.ts symlink 폴백 진단** (`src/host/install-claude.ts:67-87`)
|
|
109
|
+
- Windows 비관리자 / macOS SIP 환경에서 `fs.symlinkSync` 가 EPERM 으로 실패하면
|
|
110
|
+
조용히 cpSync 로 폴백하던 동작에 stderr 진단 메시지 1줄 추가. "왜 install 이
|
|
111
|
+
느린지" 가 사용자에게 보임.
|
|
112
|
+
|
|
113
|
+
- **[P1] CI portability matrix 확장** (`.github/workflows/ci.yml`)
|
|
114
|
+
- Node 20.0.0 / 20.10.0 / 20.x / 22.x × ubuntu/macos/windows 6개 조합으로 훅
|
|
115
|
+
스모크 잡 추가. 모든 `dist/hooks/*.js` 를 sentinel input 으로 실행해
|
|
116
|
+
SyntaxError / Cannot find module / ERR_ 발생 시 CI 실패. 회귀 즉시 감지.
|
|
117
|
+
|
|
118
|
+
### Notes
|
|
119
|
+
|
|
120
|
+
- `node:sqlite` 의존 (`src/core/session-store.ts`) 은 기존 try/catch 폴백으로 Node
|
|
121
|
+
<22.5 에서도 graceful degrade 동작 유지. session-search MCP 도구는 0건 반환.
|
|
122
|
+
- `quality-check.mjs MODULE_NOT_FOUND` 같이 사용자/타플러그인이 등록한 외부 훅이
|
|
123
|
+
worktree 에서 누락된 경우는 forgen 책임 영역 아님. `isForgenHookEntry()` 가
|
|
124
|
+
`dist/hooks/*.js` 경로만 자기 소유로 인식하므로 외부 훅 항목은 보존.
|
|
125
|
+
|
|
10
126
|
## [0.4.4] — 2026-05-06
|
|
11
127
|
|
|
128
|
+
> **⚠ 정정 (2026-05-08, ADR-007 이후)**: 본 릴리스의 ψ master gate PASS
|
|
129
|
+
> (mean +0.098, CI [+0.002, +0.222]) 주장은 **broken testbed 위 측정** 으로
|
|
130
|
+
> 확정. 두 구조 결함 (ForgenPlusMemArm 비-결합 / mem recall 메타 inject) 위에서
|
|
131
|
+
> 산출되어 LLM noise + max-selection bias 가 평균을 양수로 끌어당긴 artifact.
|
|
132
|
+
> 양쪽 결함 수정 후 재측정 (track-mem-fix N=10 sonnet) 결과는 mean ψ = −0.080,
|
|
133
|
+
> CI [−0.161, −0.000], gate FAIL. **현 시점 forgen+mem 결합은 net negative
|
|
134
|
+
> 또는 noise 영역** — qwen2.5:14b @ temp=0.3 driver 의 hallucination 분산이
|
|
135
|
+
> 결합 효과를 mask 함. Driver determinism (temp=0 + seed) 또는 더 강한 driver
|
|
136
|
+
> 적용 후 재측정까지 셀링 보류. 자세한 내용은 ADR-007 참조.
|
|
137
|
+
>
|
|
138
|
+
> δ(forgenOnly−vanilla) = +0.223 주장도 같은 testbed 위 산출이므로 같은
|
|
139
|
+
> disclaimer 대상. 단 forgenOnly arm 자체는 본 ADR fix 영향 받지 않음 (vanilla
|
|
140
|
+
> 와의 비교는 단일 arm 내부 비교라 LLM noise 가 양쪽에 균등 분포 가능성 — 단
|
|
141
|
+
> 재측정으로 확인 필요).
|
|
142
|
+
|
|
12
143
|
### v0.4.4 — measurement infra rebuild + stop-guard hardening (DANGEROUS-RESPONSE)
|
|
13
144
|
|
|
14
145
|
forgen-eval testbed 의 측정 인프라 5-layer 결함을 모두 수정해 신뢰성을 회복하고,
|
|
15
146
|
그 과정에서 발견한 driver-brittleness 결함(syn-004 — small driver 가 학습된 룰을
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
147
|
+
파괴 명령 우회로 회피)을 stop-guard `dangerous-response-pattern` 체크로 직접
|
|
148
|
+
close. 사후 N=10 재측정에서 **ψ master gate PASS** (mean +0.098, 95% CI [+0.002,
|
|
149
|
+
+0.222]) — pre-hardening (-0.028) 대비 부호 양수 전환. 또한
|
|
19
150
|
δ(forgenOnly−vanilla) = +0.223 (CI [+0.134, +0.326], 10/10 cases positive) 으로
|
|
20
|
-
forgen 효과가 robust 하게 확인됨.
|
|
151
|
+
forgen 효과가 robust 하게 확인됨. (위 박스 참조: 본 측정 결과는 ADR-007 이후
|
|
152
|
+
broken testbed artifact 로 확정.)
|
|
21
153
|
|
|
22
154
|
**Highlights**:
|
|
23
155
|
|
package/README.md
CHANGED
|
@@ -61,6 +61,19 @@ This is **Mech-B self-check prompt-inject**. It works because Claude Code's Stop
|
|
|
61
61
|
|
|
62
62
|
> **v0.4.3 self-correction story:** the same guards detected their own 16-day false-positive (strict φ 65.66% — 84% from a single Korean-regex bug), and the [`forgen-eval`](packages/forgen-eval/) introspect testbed (alpha) flagged a `TEST-1` wiring gap on top of it. Both fixes shipped in v0.4.3 — forgen finding and fixing forgen. Details in [CHANGELOG](CHANGELOG.md).
|
|
63
63
|
|
|
64
|
+
> **v0.4.5 measurement evidence (statistically proven):** with all testbed
|
|
65
|
+
> structural fixes applied ([ADR-007](docs/adr/ADR-007-testbed-arm-isolation.md)),
|
|
66
|
+
> forgen's effect over a vanilla baseline is **statistically significant on real
|
|
67
|
+
> production drivers (Claude sonnet, Codex)**. Pooled across both drivers
|
|
68
|
+
> (retry+sequential N=33 each, N=66 total): **mean δ = +0.151 W, 95% CI [+0.118,
|
|
69
|
+
> +0.184], 62/66 (93.9%) cases positive, sign test p = 1.04×10⁻¹⁴**. Codex alone:
|
|
70
|
+
> mean δ = +0.176, 32/33 (97%) positive, p = 4×10⁻⁹. Claude alone: mean δ =
|
|
71
|
+
> +0.125, 30/33 (91%) positive, p = 7×10⁻⁷. **Three independent measurements
|
|
72
|
+
> across two model families all prove δ > 0**. v0.4.4's ψ-master-gate PASS claim
|
|
73
|
+
> is rescinded as a broken-testbed artifact; ψ (forgen+mem coexistence) is
|
|
74
|
+
> confirmed as ≈0 — **forgen alone is the recommended path**. See
|
|
75
|
+
> [`docs/release/v0.4.5-draft.md`](docs/release/v0.4.5-draft.md).
|
|
76
|
+
|
|
64
77
|
🎬 **See it happen** (27 seconds):
|
|
65
78
|
|
|
66
79
|
```bash
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: forge-loop
|
|
3
|
-
description: This skill should be used when the user asks to "forge-loop, 포지루프, 끝까지, don't stop".
|
|
4
|
-
argument-hint: "[task description]"
|
|
3
|
+
description: This skill should be used when the user asks to "forge-loop, 포지루프, 끝까지, don't stop, goal, 목표, goal lock, scope lock". 작업을 PRD(User Story)로 분해 + 모든 수용 기준 충족까지 반복 실행. `--goal-only` 플래그로 PRD/수용기준 박제만 (실행 사이클 없이) 가능 — goal-locking pattern lightweight 진입점.
|
|
4
|
+
argument-hint: "[task description] [--goal-only]"
|
|
5
5
|
model: inherit
|
|
6
6
|
allowed-tools:
|
|
7
7
|
- Read
|
|
@@ -18,6 +18,12 @@ triggers:
|
|
|
18
18
|
- "don't stop"
|
|
19
19
|
- "완료될 때까지"
|
|
20
20
|
- "루프로 실행"
|
|
21
|
+
- "goal"
|
|
22
|
+
- "목표"
|
|
23
|
+
- "goal lock"
|
|
24
|
+
- "scope lock"
|
|
25
|
+
- "completion criteria"
|
|
26
|
+
- "수용 기준"
|
|
21
27
|
---
|
|
22
28
|
|
|
23
29
|
<Purpose>
|
|
@@ -90,6 +96,35 @@ EOF
|
|
|
90
96
|
이 파일이 있어야 Claude가 중간에 멈추지 않도록 Stop 훅이 차단합니다.
|
|
91
97
|
스토리 완료 시 `passes: true`로 업데이트. 전체 완료는 Stop 훅이 자동 처리.
|
|
92
98
|
|
|
99
|
+
### goal-only 모드 — Phase 1 종료 분기
|
|
100
|
+
|
|
101
|
+
`$ARGUMENTS` 에 `--goal-only` / `--goal` / `--lock-only` 중 하나가 포함된 경우,
|
|
102
|
+
Phase 1 종료 직후 다음을 산출하고 종료 (Phase 2/3 건너뜀):
|
|
103
|
+
|
|
104
|
+
1. 위 PRD JSON 의 stories 배열을 markdown Goal 박스로 변환:
|
|
105
|
+
```
|
|
106
|
+
GOAL: <stories[0].title — 단일 story 면 한 문장 요약>
|
|
107
|
+
완료 기준 (Acceptance Criteria):
|
|
108
|
+
- [ ] <story[i].acceptanceCriteria[j] 각각 — 구체적 증거 타입 포함>
|
|
109
|
+
제약 (Out-of-Scope):
|
|
110
|
+
- <"수용 기준 품질 규칙" 표의 금지 패턴들>
|
|
111
|
+
- <사용자가 명시한 dry-run / touch 안 할 경로 등>
|
|
112
|
+
검증 방법:
|
|
113
|
+
- <각 AC 의 verification command (bash / curl / file check)>
|
|
114
|
+
컴파운드 패턴 (참고):
|
|
115
|
+
- <compound-search top 1-2 결과 — 본 작업 키워드로 검색>
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
2. 사용자에게 박스를 보여주고 안내:
|
|
119
|
+
```
|
|
120
|
+
GOAL 박제 완료. 다음 옵션:
|
|
121
|
+
- 이 박스를 다른 컨텍스트/에이전트에 위임 → 복사 사용
|
|
122
|
+
- 본 세션에서 자동 실행 → `forge-loop resume` 로 Phase 2 이어 실행
|
|
123
|
+
상태 파일: ~/.forgen/state/forge-loop.json (resume 시 재활용)
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
3. 종료. **Anti-Polite-Stop 규칙은 goal-only 모드에 적용 안 함** — 박제가 목적이고 실행은 명시적 escalation 시에만.
|
|
127
|
+
|
|
93
128
|
## Phase 2: 스토리 실행 루프
|
|
94
129
|
|
|
95
130
|
### 2-1. Compound-In (스토리별)
|
|
@@ -210,6 +245,31 @@ compound에 저장하시겠습니까? [Y/n]
|
|
|
210
245
|
<Arguments>
|
|
211
246
|
- `[task description]`: 실행할 작업 설명. 생략 시 현재 대화 컨텍스트에서 추론.
|
|
212
247
|
- `resume`: 이전에 중단된 루프를 재개합니다.
|
|
248
|
+
- `--goal-only` (또는 `--goal`, `--lock-only`): **goal-locking lightweight 모드**.
|
|
249
|
+
Phase 1 (PRD + 수용 기준 + 상태 파일 저장) 까지만 실행하고 Phase 2/3 (자동
|
|
250
|
+
실행 루프 + 최종 검증) 은 건너뜁니다. 산출물은 *구조화된 Goal 박스* — 작업
|
|
251
|
+
범위 / 완료 기준 / 제약 / 검증 방법을 한 markdown 으로 박제. 사용자가 다른
|
|
252
|
+
컨텍스트나 에이전트에 그대로 붙여 위임 가능. 추후 `forge-loop resume` 로
|
|
253
|
+
자동 실행 사이클 escalate 가능 (상태 파일 재활용).
|
|
254
|
+
|
|
255
|
+
goal-only 모드의 산출물 포맷:
|
|
256
|
+
```
|
|
257
|
+
GOAL: <한 문장 요약>
|
|
258
|
+
완료 기준 (Acceptance Criteria — 증거 타입 포함):
|
|
259
|
+
- [ ] AC1: <테스트 로그 / 파일 변경 / dry-run 출력>
|
|
260
|
+
- [ ] AC2: ...
|
|
261
|
+
제약 (Out-of-Scope / 안 할 것):
|
|
262
|
+
- <실 발송·배포·삭제 금지 / dry-run 한정>
|
|
263
|
+
- <touch 안 할 경로>
|
|
264
|
+
검증 방법:
|
|
265
|
+
- <bash 명령 / 파일 확인 / 외부 verification>
|
|
266
|
+
컴파운드 패턴 (참고):
|
|
267
|
+
- <compound-search 결과 top 1-2>
|
|
268
|
+
```
|
|
269
|
+
|
|
270
|
+
goal-only 모드는 stop-guard 의 fact-vs-agreement / self-score-inflation
|
|
271
|
+
체크와 직접 연동 — Goal 박스 박제 후 응답이 "완료" 주장 시 AC 의 증거가
|
|
272
|
+
포함되어야 통과.
|
|
213
273
|
</Arguments>
|
|
214
274
|
|
|
215
275
|
$ARGUMENTS
|
package/dist/cli.js
CHANGED
|
@@ -95,6 +95,14 @@ const commands = [
|
|
|
95
95
|
await handleInspect(['profile']);
|
|
96
96
|
},
|
|
97
97
|
},
|
|
98
|
+
{
|
|
99
|
+
name: 'statusline',
|
|
100
|
+
description: 'Compact HUD for Claude Code statusLine (reads stdin JSON)',
|
|
101
|
+
handler: async (_args) => {
|
|
102
|
+
const { handleStatusline } = await import('./core/statusline-cli.js');
|
|
103
|
+
await handleStatusline();
|
|
104
|
+
},
|
|
105
|
+
},
|
|
98
106
|
{
|
|
99
107
|
name: 'config',
|
|
100
108
|
description: 'Configuration (hooks [--regenerate])',
|
|
@@ -43,12 +43,18 @@ function readSettingsWithBackup() {
|
|
|
43
43
|
}
|
|
44
44
|
return settings;
|
|
45
45
|
}
|
|
46
|
-
/** Apply forgen statusLine only if user hasn't set a custom one.
|
|
46
|
+
/** Apply forgen statusLine only if user hasn't set a custom one.
|
|
47
|
+
* Migration: 'forgen me' → 'forgen statusline' (multi-line dump → compact HUD). */
|
|
47
48
|
function applyStatusLine(settings) {
|
|
48
49
|
const existing = settings.statusLine;
|
|
50
|
+
// 기존에 'forgen me'로 주입된 경우 → 'forgen statusline'으로 자동 마이그레이션
|
|
51
|
+
if (existing?.command === 'forgen me') {
|
|
52
|
+
settings.statusLine = { type: 'command', command: 'forgen statusline' };
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
49
55
|
const isForgenOwned = !existing || !existing.command || existing.command.startsWith('forgen');
|
|
50
56
|
if (isForgenOwned) {
|
|
51
|
-
settings.statusLine = { type: 'command', command: 'forgen
|
|
57
|
+
settings.statusLine = { type: 'command', command: 'forgen statusline' };
|
|
52
58
|
}
|
|
53
59
|
}
|
|
54
60
|
/** Check if a settings.json hook entry was installed by forgen. */
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* forgen statusline — Claude Code statusLine 명령
|
|
3
|
+
*
|
|
4
|
+
* Claude Code는 statusLine.command를 주기적으로 호출하고 stdin에 JSON을 전달함.
|
|
5
|
+
* 이 명령은 compact multi-line 형식으로 HUD 정보를 출력함.
|
|
6
|
+
*
|
|
7
|
+
* Line 1: 모델 | cwd | git branch
|
|
8
|
+
* Line 2: (TODO: context/usage — stdin spec 미확인으로 생략)
|
|
9
|
+
* Line 3: CLAUDE.md count | rules count | MCPs count | hooks count
|
|
10
|
+
* Line 4: (TODO: tool counts — 추적 인프라 없음)
|
|
11
|
+
* Line 5: (TODO: active task — 추적 인프라 없음)
|
|
12
|
+
*/
|
|
13
|
+
export declare function handleStatusline(): Promise<void>;
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* forgen statusline — Claude Code statusLine 명령
|
|
3
|
+
*
|
|
4
|
+
* Claude Code는 statusLine.command를 주기적으로 호출하고 stdin에 JSON을 전달함.
|
|
5
|
+
* 이 명령은 compact multi-line 형식으로 HUD 정보를 출력함.
|
|
6
|
+
*
|
|
7
|
+
* Line 1: 모델 | cwd | git branch
|
|
8
|
+
* Line 2: (TODO: context/usage — stdin spec 미확인으로 생략)
|
|
9
|
+
* Line 3: CLAUDE.md count | rules count | MCPs count | hooks count
|
|
10
|
+
* Line 4: (TODO: tool counts — 추적 인프라 없음)
|
|
11
|
+
* Line 5: (TODO: active task — 추적 인프라 없음)
|
|
12
|
+
*/
|
|
13
|
+
import * as fs from 'node:fs';
|
|
14
|
+
import * as path from 'node:path';
|
|
15
|
+
import * as os from 'node:os';
|
|
16
|
+
import { execSync } from 'node:child_process';
|
|
17
|
+
import { loadActiveRules } from '../store/rule-store.js';
|
|
18
|
+
// ANSI codes
|
|
19
|
+
const DIM = '\x1b[2m';
|
|
20
|
+
const CYAN = '\x1b[36m';
|
|
21
|
+
const GREEN = '\x1b[32m';
|
|
22
|
+
const YELLOW = '\x1b[33m';
|
|
23
|
+
const BOLD = '\x1b[1m';
|
|
24
|
+
const RESET = '\x1b[0m';
|
|
25
|
+
function readStdinJson() {
|
|
26
|
+
// stdin이 TTY면 파이프 입력 없음 → 빈 payload로 fallback
|
|
27
|
+
if (process.stdin.isTTY)
|
|
28
|
+
return {};
|
|
29
|
+
try {
|
|
30
|
+
const raw = fs.readFileSync('/dev/stdin', 'utf-8').trim();
|
|
31
|
+
if (!raw)
|
|
32
|
+
return {};
|
|
33
|
+
return JSON.parse(raw);
|
|
34
|
+
}
|
|
35
|
+
catch {
|
|
36
|
+
return {};
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
function getGitBranch(cwd) {
|
|
40
|
+
try {
|
|
41
|
+
const branch = execSync('git rev-parse --abbrev-ref HEAD', {
|
|
42
|
+
cwd,
|
|
43
|
+
stdio: ['ignore', 'pipe', 'ignore'],
|
|
44
|
+
timeout: 2000,
|
|
45
|
+
})
|
|
46
|
+
.toString()
|
|
47
|
+
.trim();
|
|
48
|
+
const isDirty = (() => {
|
|
49
|
+
try {
|
|
50
|
+
const status = execSync('git status --porcelain', {
|
|
51
|
+
cwd,
|
|
52
|
+
stdio: ['ignore', 'pipe', 'ignore'],
|
|
53
|
+
timeout: 2000,
|
|
54
|
+
}).toString().trim();
|
|
55
|
+
return status.length > 0;
|
|
56
|
+
}
|
|
57
|
+
catch {
|
|
58
|
+
return false;
|
|
59
|
+
}
|
|
60
|
+
})();
|
|
61
|
+
return `git:(${branch}${isDirty ? '*' : ''})`;
|
|
62
|
+
}
|
|
63
|
+
catch {
|
|
64
|
+
return '';
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
function getSettingsJson(claudeDir) {
|
|
68
|
+
const settingsPath = path.join(claudeDir, 'settings.json');
|
|
69
|
+
if (!fs.existsSync(settingsPath))
|
|
70
|
+
return {};
|
|
71
|
+
try {
|
|
72
|
+
return JSON.parse(fs.readFileSync(settingsPath, 'utf-8'));
|
|
73
|
+
}
|
|
74
|
+
catch {
|
|
75
|
+
return {};
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
function countMcps(settings) {
|
|
79
|
+
const mcpServers = settings.mcpServers;
|
|
80
|
+
if (!mcpServers || typeof mcpServers !== 'object')
|
|
81
|
+
return 0;
|
|
82
|
+
return Object.keys(mcpServers).length;
|
|
83
|
+
}
|
|
84
|
+
function countHooks(settings) {
|
|
85
|
+
const hooks = settings.hooks;
|
|
86
|
+
if (!hooks || typeof hooks !== 'object')
|
|
87
|
+
return 0;
|
|
88
|
+
return Object.values(hooks).reduce((acc, matchers) => {
|
|
89
|
+
if (!Array.isArray(matchers))
|
|
90
|
+
return acc;
|
|
91
|
+
return acc + matchers.length;
|
|
92
|
+
}, 0);
|
|
93
|
+
}
|
|
94
|
+
function countClaudeMd(cwd) {
|
|
95
|
+
try {
|
|
96
|
+
const result = execSync('find . -maxdepth 2 -name CLAUDE.md', {
|
|
97
|
+
cwd,
|
|
98
|
+
stdio: ['ignore', 'pipe', 'ignore'],
|
|
99
|
+
timeout: 3000,
|
|
100
|
+
}).toString().trim();
|
|
101
|
+
if (!result)
|
|
102
|
+
return 0;
|
|
103
|
+
return result.split('\n').filter(Boolean).length;
|
|
104
|
+
}
|
|
105
|
+
catch {
|
|
106
|
+
return 0;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
function buildLine1(payload, cwd) {
|
|
110
|
+
const modelName = payload.model?.display_name ?? 'Claude';
|
|
111
|
+
const gitBranch = getGitBranch(cwd);
|
|
112
|
+
const cwdDisplay = cwd.replace(os.homedir(), '~');
|
|
113
|
+
const parts = [`${BOLD}${CYAN}${modelName}${RESET}`];
|
|
114
|
+
parts.push(`${DIM}${cwdDisplay}${RESET}`);
|
|
115
|
+
if (gitBranch)
|
|
116
|
+
parts.push(`${GREEN}${gitBranch}${RESET}`);
|
|
117
|
+
return parts.join(` ${DIM}|${RESET} `);
|
|
118
|
+
}
|
|
119
|
+
function buildLine3(claudeDir, cwd) {
|
|
120
|
+
const settings = getSettingsJson(claudeDir);
|
|
121
|
+
const claudeMdCount = countClaudeMd(cwd);
|
|
122
|
+
const rulesCount = (() => {
|
|
123
|
+
try {
|
|
124
|
+
return loadActiveRules().length;
|
|
125
|
+
}
|
|
126
|
+
catch {
|
|
127
|
+
return 0;
|
|
128
|
+
}
|
|
129
|
+
})();
|
|
130
|
+
const mcpCount = countMcps(settings);
|
|
131
|
+
const hookCount = countHooks(settings);
|
|
132
|
+
return [
|
|
133
|
+
`${YELLOW}${claudeMdCount} CLAUDE.md${RESET}`,
|
|
134
|
+
`${YELLOW}${rulesCount} rules${RESET}`,
|
|
135
|
+
`${YELLOW}${mcpCount} MCPs${RESET}`,
|
|
136
|
+
`${YELLOW}${hookCount} hooks${RESET}`,
|
|
137
|
+
].join(` ${DIM}|${RESET} `);
|
|
138
|
+
}
|
|
139
|
+
export async function handleStatusline() {
|
|
140
|
+
const payload = readStdinJson();
|
|
141
|
+
const cwd = payload.workspace?.current_dir ?? process.cwd();
|
|
142
|
+
const claudeDir = path.join(os.homedir(), '.claude');
|
|
143
|
+
const line1 = buildLine1(payload, cwd);
|
|
144
|
+
const line3 = buildLine3(claudeDir, cwd);
|
|
145
|
+
// Line 2 (context/usage): stdin JSON spec 미확인으로 생략 — TODO
|
|
146
|
+
// Line 4 (tool counts): 추적 인프라 없음 — TODO
|
|
147
|
+
// Line 5 (active task): 추적 인프라 없음 — TODO
|
|
148
|
+
console.log(line1);
|
|
149
|
+
console.log(line3);
|
|
150
|
+
}
|
|
@@ -10,8 +10,9 @@
|
|
|
10
10
|
* - safety: 범용 안전 훅 (기본 활성, 개별 비활성 가능)
|
|
11
11
|
* - workflow: 워크플로우 스킬 훅 (다른 플러그인 감지 시 자동 비활성)
|
|
12
12
|
*/
|
|
13
|
-
import {
|
|
14
|
-
|
|
13
|
+
import { readFileSync } from 'node:fs';
|
|
14
|
+
import { fileURLToPath } from 'node:url';
|
|
15
|
+
import { dirname, join } from 'node:path';
|
|
15
16
|
/**
|
|
16
17
|
* 단일 소스 오브 트루스: hooks/hook-registry.json
|
|
17
18
|
*
|
|
@@ -19,9 +20,13 @@ const require = createRequire(import.meta.url);
|
|
|
19
20
|
* - pre-tool-use는 db-guard/rate-limiter보다 앞에 위치
|
|
20
21
|
* (Code Reflection + permission hints 주입 타이밍)
|
|
21
22
|
* - 같은 이벤트 내 훅은 배열 순서대로 실행됨
|
|
23
|
+
*
|
|
24
|
+
* Why readFileSync (not `import ... with { type: 'json' }`):
|
|
25
|
+
* Import attributes는 Node 20.10+에서만 파싱됨. 20.0-20.9 사용자가 npm i -g
|
|
26
|
+
* 이후 모든 훅이 SyntaxError로 깨지는 것을 방지하기 위해 fs.readFileSync 사용.
|
|
22
27
|
*/
|
|
23
|
-
import
|
|
24
|
-
export const HOOK_REGISTRY =
|
|
28
|
+
const REGISTRY_PATH = join(dirname(fileURLToPath(import.meta.url)), '..', '..', 'assets', 'shared', 'hook-registry.json');
|
|
29
|
+
export const HOOK_REGISTRY = JSON.parse(readFileSync(REGISTRY_PATH, 'utf-8'));
|
|
25
30
|
/** 티어별 훅 목록 조회 */
|
|
26
31
|
export function getHooksByTier(tier) {
|
|
27
32
|
return HOOK_REGISTRY.filter(h => h.tier === tier);
|
|
@@ -40,13 +40,21 @@ function writePluginCache(opts) {
|
|
|
40
40
|
catch { /* ignore */ }
|
|
41
41
|
fs.mkdirSync(cacheParent, { recursive: true });
|
|
42
42
|
// 1차: symlink 시도 (개발 환경)
|
|
43
|
+
// Why warn on fallback: Windows 비관리자 / macOS SIP 환경에서 symlink 가 EPERM
|
|
44
|
+
// 으로 거부되면 조용히 cpSync 폴백을 탔는데, 사용자는 "왜 install 이 느리지"
|
|
45
|
+
// 를 알 길이 없었다. 폴백 진입을 stderr 로 알려서 진단성 확보.
|
|
43
46
|
let linked = false;
|
|
47
|
+
let symlinkErr = null;
|
|
44
48
|
try {
|
|
45
49
|
fs.symlinkSync(pkgRoot, cacheDir, 'dir');
|
|
46
50
|
linked = true;
|
|
47
51
|
}
|
|
48
|
-
catch {
|
|
49
|
-
|
|
52
|
+
catch (e) {
|
|
53
|
+
symlinkErr = e;
|
|
54
|
+
}
|
|
55
|
+
if (!linked && symlinkErr) {
|
|
56
|
+
const code = symlinkErr.code ?? 'UNKNOWN';
|
|
57
|
+
process.stderr.write(`[forgen] symlink ${pkgRoot} → ${cacheDir} failed (${code}); falling back to cpSync.\n`);
|
|
50
58
|
}
|
|
51
59
|
if (!linked) {
|
|
52
60
|
fs.mkdirSync(cacheDir, { recursive: true });
|
|
@@ -91,6 +99,29 @@ function writePluginCache(opts) {
|
|
|
91
99
|
return true;
|
|
92
100
|
}
|
|
93
101
|
// ── 2. Slash commands ──────────────────────────────────────────────────
|
|
102
|
+
/** Build-time injected --with-codex shared snippet. Mirror of scripts/copy-assets.js. */
|
|
103
|
+
const WITH_CODEX_SNIPPET = `
|
|
104
|
+
|
|
105
|
+
---
|
|
106
|
+
|
|
107
|
+
## \`--with-codex\` flag (cross-model review)
|
|
108
|
+
|
|
109
|
+
If \`$ARGUMENTS\` contains any of \`--with-codex\`, \`--코덱스\`, \`with codex\`, \`코덱스 검토\`, \`코덱스로 검토\`,
|
|
110
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
111
|
+
|
|
112
|
+
1. Save your primary output text to a temp file (e.g., \`/tmp/forgen-with-codex-$(date +%s).md\`).
|
|
113
|
+
2. Invoke codex via Bash:
|
|
114
|
+
\`\`\`bash
|
|
115
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \\
|
|
116
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \\
|
|
117
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\\\u0027s output. Read the work product below and report ONLY:\\n1. Defects, gaps, or risks the original work missed\\n2. Specific disagreements with the original\\n3. Topics that should have been covered but were not\\n\\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\\n\\n<work>\\n%s\\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
118
|
+
\`\`\`
|
|
119
|
+
3. Append the codex output under heading \`## Codex Cross-Review (--with-codex)\` in your final response.
|
|
120
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
121
|
+
5. If \`codex: command not found\`, note in response and skip the review pass (do not fail).
|
|
122
|
+
|
|
123
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
124
|
+
`;
|
|
94
125
|
function writeSlashCommands(opts) {
|
|
95
126
|
const { pkgRoot, targetDir, dryRun } = opts;
|
|
96
127
|
const sourceDir = path.join(pkgRoot, 'assets', 'claude', 'commands');
|
|
@@ -106,7 +137,7 @@ function writeSlashCommands(opts) {
|
|
|
106
137
|
const descMatch = skillContent.match(/description:\s*(.+)/);
|
|
107
138
|
const desc = descMatch?.[1]?.trim() ?? file.replace(/\.md$/, '');
|
|
108
139
|
const skillName = file.replace(/\.md$/, '');
|
|
109
|
-
const out = `# ${desc}\n\n${FORGEN_MANAGED_MARKER}\n\nActivate Forgen "${skillName}" mode for the task: $ARGUMENTS\n\n${skillContent}`;
|
|
140
|
+
const out = `# ${desc}\n\n${FORGEN_MANAGED_MARKER}\n\nActivate Forgen "${skillName}" mode for the task: $ARGUMENTS\n\n${skillContent}${WITH_CODEX_SNIPPET}`;
|
|
110
141
|
const target = path.join(targetDir, file);
|
|
111
142
|
if (fs.existsSync(target)) {
|
|
112
143
|
const existing = fs.readFileSync(target, 'utf-8');
|
package/package.json
CHANGED
package/plugin.json
CHANGED
package/scripts/postinstall.js
CHANGED
|
@@ -516,10 +516,34 @@ function generateAndWriteHooksJson() {
|
|
|
516
516
|
}
|
|
517
517
|
|
|
518
518
|
// ── 4. Install slash commands ──
|
|
519
|
+
/** Build-time injected --with-codex shared snippet. Mirror of scripts/copy-assets.js. */
|
|
520
|
+
const WITH_CODEX_SNIPPET = `
|
|
521
|
+
|
|
522
|
+
---
|
|
523
|
+
|
|
524
|
+
## \`--with-codex\` flag (cross-model review)
|
|
525
|
+
|
|
526
|
+
If \`$ARGUMENTS\` contains any of \`--with-codex\`, \`--코덱스\`, \`with codex\`, \`코덱스 검토\`, \`코덱스로 검토\`,
|
|
527
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
528
|
+
|
|
529
|
+
1. Save your primary output text to a temp file (e.g., \`/tmp/forgen-with-codex-$(date +%s).md\`).
|
|
530
|
+
2. Invoke codex via Bash:
|
|
531
|
+
\`\`\`bash
|
|
532
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \\
|
|
533
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \\
|
|
534
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\\\u0027s output. Read the work product below and report ONLY:\\n1. Defects, gaps, or risks the original work missed\\n2. Specific disagreements with the original\\n3. Topics that should have been covered but were not\\n\\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\\n\\n<work>\\n%s\\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
535
|
+
\`\`\`
|
|
536
|
+
3. Append the codex output under heading \`## Codex Cross-Review (--with-codex)\` in your final response.
|
|
537
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
538
|
+
5. If \`codex: command not found\`, note in response and skip the review pass (do not fail).
|
|
539
|
+
|
|
540
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
541
|
+
`;
|
|
542
|
+
|
|
519
543
|
function buildCommandContent(skillContent, skillName) {
|
|
520
544
|
const descMatch = skillContent.match(/description:\s*(.+)/);
|
|
521
545
|
const desc = descMatch?.[1]?.trim() ?? skillName;
|
|
522
|
-
return `# ${desc}\n\n<!-- forgen-managed -->\n\nActivate Forgen "${skillName}" mode for the task: $ARGUMENTS\n\n${skillContent}`;
|
|
546
|
+
return `# ${desc}\n\n<!-- forgen-managed -->\n\nActivate Forgen "${skillName}" mode for the task: $ARGUMENTS\n\n${skillContent}${WITH_CODEX_SNIPPET}`;
|
|
523
547
|
}
|
|
524
548
|
|
|
525
549
|
function safeWriteCommand(cmdPath, content) {
|
|
@@ -729,7 +753,7 @@ function cleanLegacyMcpFromSettings(settings) {
|
|
|
729
753
|
* 이전 방식(3곳에서 각각 read-modify-write)은 중간에 다른 프로세스가
|
|
730
754
|
* settings.json을 수정하면 데이터 유실 가능성이 있었습니다.
|
|
731
755
|
*/
|
|
732
|
-
function main() {
|
|
756
|
+
async function main() {
|
|
733
757
|
// W-V2: 로컬 설치 시 전역 설정 수정 방지
|
|
734
758
|
if (!process.env.npm_config_global && process.env.INIT_CWD && process.env.INIT_CWD !== PKG_ROOT) {
|
|
735
759
|
// npm install (로컬) — postinstall 스킵
|
|
@@ -906,6 +930,39 @@ function main() {
|
|
|
906
930
|
// sudo 실행 시 파일 소유권을 실제 유저로 변경
|
|
907
931
|
fixOwnership(join(HOME, '.claude'), join(HOME, '.forgen'));
|
|
908
932
|
|
|
933
|
+
// ── 9. Self-check: 설치 산출물이 현재 Node 에서 실제로 로드되는지 확인 ──
|
|
934
|
+
//
|
|
935
|
+
// Why: 0.4.4 이전 빌드는 `import ... with { type: 'json' }` 를 사용해 Node
|
|
936
|
+
// 20.0-20.9 에서 모든 훅이 SyntaxError 로 깨졌다. 사용자는 npm i -g 가 정상
|
|
937
|
+
// 종료된 직후에야 "각종 훅들이 에러난다"는 증상을 보았다. self-check 가 있었
|
|
938
|
+
// 다면 install 시점에 즉시 실패를 노출했을 것.
|
|
939
|
+
//
|
|
940
|
+
// 동작: dist/hooks/hook-registry.js 를 dynamic import 로 로드 → HOOK_REGISTRY
|
|
941
|
+
// 배열에 entry 가 있는지 확인. 실패 시 stderr 로 구체적 원인 + Node 버전을
|
|
942
|
+
// 알리고 npm install 자체는 깨뜨리지 않음 (postinstall 정책 유지).
|
|
943
|
+
let selfCheckOk = false;
|
|
944
|
+
let selfCheckErr = '';
|
|
945
|
+
try {
|
|
946
|
+
const registryUrl = new URL('../dist/hooks/hook-registry.js', import.meta.url);
|
|
947
|
+
const mod = await import(registryUrl.href);
|
|
948
|
+
if (Array.isArray(mod?.HOOK_REGISTRY) && mod.HOOK_REGISTRY.length > 0) {
|
|
949
|
+
selfCheckOk = true;
|
|
950
|
+
} else {
|
|
951
|
+
selfCheckErr = 'HOOK_REGISTRY is empty or not an array';
|
|
952
|
+
}
|
|
953
|
+
} catch (err) {
|
|
954
|
+
selfCheckErr = err?.message ?? String(err);
|
|
955
|
+
}
|
|
956
|
+
if (!selfCheckOk) {
|
|
957
|
+
console.error('');
|
|
958
|
+
console.error(`[forgen] WARNING: hook self-check FAILED on Node ${process.version}.`);
|
|
959
|
+
console.error(`[forgen] reason: ${selfCheckErr}`);
|
|
960
|
+
console.error('[forgen] 훅이 Claude Code 실행 시 로드 실패할 수 있습니다.');
|
|
961
|
+
console.error('[forgen] Node 20.10+ 또는 22.x 사용을 권장합니다.');
|
|
962
|
+
console.error('[forgen] 문제 지속 시: https://github.com/forgen-team/forgen/issues');
|
|
963
|
+
console.error('');
|
|
964
|
+
}
|
|
965
|
+
|
|
909
966
|
const parts = [];
|
|
910
967
|
if (plugin) parts.push('plugin');
|
|
911
968
|
if (hooksJsonResult) parts.push(`hooks.json (${hooksJsonResult.active}/${hooksJsonResult.total} active)`);
|
|
@@ -940,9 +997,7 @@ function main() {
|
|
|
940
997
|
}
|
|
941
998
|
}
|
|
942
999
|
|
|
943
|
-
|
|
944
|
-
main();
|
|
945
|
-
} catch (err) {
|
|
1000
|
+
main().catch((err) => {
|
|
946
1001
|
// postinstall 실패가 npm install을 깨뜨리지 않되, 원인은 표시
|
|
947
1002
|
console.error(`[forgen] postinstall warning: ${err?.message ?? err}`);
|
|
948
|
-
}
|
|
1003
|
+
});
|
|
@@ -163,3 +163,24 @@ Positive / Negative / Risks / Follow-up
|
|
|
163
163
|
</Arguments>
|
|
164
164
|
|
|
165
165
|
$ARGUMENTS
|
|
166
|
+
|
|
167
|
+
---
|
|
168
|
+
|
|
169
|
+
## `--with-codex` flag (cross-model review)
|
|
170
|
+
|
|
171
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
172
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
173
|
+
|
|
174
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
175
|
+
2. Invoke codex via Bash:
|
|
176
|
+
```bash
|
|
177
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
178
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
179
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
180
|
+
```
|
|
181
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
182
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
183
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
184
|
+
|
|
185
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
186
|
+
|
|
@@ -206,3 +206,24 @@ Compound 교차 검증:
|
|
|
206
206
|
</Arguments>
|
|
207
207
|
|
|
208
208
|
$ARGUMENTS
|
|
209
|
+
|
|
210
|
+
---
|
|
211
|
+
|
|
212
|
+
## `--with-codex` flag (cross-model review)
|
|
213
|
+
|
|
214
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
215
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
216
|
+
|
|
217
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
218
|
+
2. Invoke codex via Bash:
|
|
219
|
+
```bash
|
|
220
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
221
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
222
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
223
|
+
```
|
|
224
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
225
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
226
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
227
|
+
|
|
228
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
229
|
+
|
|
@@ -199,3 +199,24 @@ VERDICT: {APPROVE / REQUEST CHANGES / COMMENT}
|
|
|
199
199
|
</Arguments>
|
|
200
200
|
|
|
201
201
|
$ARGUMENTS
|
|
202
|
+
|
|
203
|
+
---
|
|
204
|
+
|
|
205
|
+
## `--with-codex` flag (cross-model review)
|
|
206
|
+
|
|
207
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
208
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
209
|
+
|
|
210
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
211
|
+
2. Invoke codex via Bash:
|
|
212
|
+
```bash
|
|
213
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
214
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
215
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
216
|
+
```
|
|
217
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
218
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
219
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
220
|
+
|
|
221
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
222
|
+
|
package/skills/compound/SKILL.md
CHANGED
|
@@ -157,3 +157,24 @@ NEVER: **Health Dashboard 건너뛰기**: 추출 후 반드시 Phase 5 실행.
|
|
|
157
157
|
</Arguments>
|
|
158
158
|
|
|
159
159
|
$ARGUMENTS
|
|
160
|
+
|
|
161
|
+
---
|
|
162
|
+
|
|
163
|
+
## `--with-codex` flag (cross-model review)
|
|
164
|
+
|
|
165
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
166
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
167
|
+
|
|
168
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
169
|
+
2. Invoke codex via Bash:
|
|
170
|
+
```bash
|
|
171
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
172
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
173
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
174
|
+
```
|
|
175
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
176
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
177
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
178
|
+
|
|
179
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
180
|
+
|
|
@@ -264,3 +264,24 @@ NEVER: **챌린지 모드 건너뛰기**: Round 4+ 이후 반드시 적용.
|
|
|
264
264
|
</Arguments>
|
|
265
265
|
|
|
266
266
|
$ARGUMENTS
|
|
267
|
+
|
|
268
|
+
---
|
|
269
|
+
|
|
270
|
+
## `--with-codex` flag (cross-model review)
|
|
271
|
+
|
|
272
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
273
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
274
|
+
|
|
275
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
276
|
+
2. Invoke codex via Bash:
|
|
277
|
+
```bash
|
|
278
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
279
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
280
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
281
|
+
```
|
|
282
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
283
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
284
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
285
|
+
|
|
286
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
287
|
+
|
package/skills/docker/SKILL.md
CHANGED
|
@@ -144,3 +144,24 @@ SECURITY SCAN / 보안 스캔
|
|
|
144
144
|
</Arguments>
|
|
145
145
|
|
|
146
146
|
$ARGUMENTS
|
|
147
|
+
|
|
148
|
+
---
|
|
149
|
+
|
|
150
|
+
## `--with-codex` flag (cross-model review)
|
|
151
|
+
|
|
152
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
153
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
154
|
+
|
|
155
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
156
|
+
2. Invoke codex via Bash:
|
|
157
|
+
```bash
|
|
158
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
159
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
160
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
161
|
+
```
|
|
162
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
163
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
164
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
165
|
+
|
|
166
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
167
|
+
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: forge-loop
|
|
3
|
-
description: This skill should be used when the user asks to "forge-loop, 포지루프, 끝까지, don't stop".
|
|
3
|
+
description: This skill should be used when the user asks to "forge-loop, 포지루프, 끝까지, don't stop, goal, 목표, goal lock, scope lock". 작업을 PRD(User Story)로 분해 + 모든 수용 기준 충족까지 반복 실행. `--goal-only` 플래그로 PRD/수용기준 박제만 (실행 사이클 없이) 가능 — goal-locking pattern lightweight 진입점.
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
<Purpose>
|
|
@@ -73,6 +73,35 @@ EOF
|
|
|
73
73
|
이 파일이 있어야 Claude가 중간에 멈추지 않도록 Stop 훅이 차단합니다.
|
|
74
74
|
스토리 완료 시 `passes: true`로 업데이트. 전체 완료는 Stop 훅이 자동 처리.
|
|
75
75
|
|
|
76
|
+
### goal-only 모드 — Phase 1 종료 분기
|
|
77
|
+
|
|
78
|
+
`$ARGUMENTS` 에 `--goal-only` / `--goal` / `--lock-only` 중 하나가 포함된 경우,
|
|
79
|
+
Phase 1 종료 직후 다음을 산출하고 종료 (Phase 2/3 건너뜀):
|
|
80
|
+
|
|
81
|
+
1. 위 PRD JSON 의 stories 배열을 markdown Goal 박스로 변환:
|
|
82
|
+
```
|
|
83
|
+
GOAL: <stories[0].title — 단일 story 면 한 문장 요약>
|
|
84
|
+
완료 기준 (Acceptance Criteria):
|
|
85
|
+
- [ ] <story[i].acceptanceCriteria[j] 각각 — 구체적 증거 타입 포함>
|
|
86
|
+
제약 (Out-of-Scope):
|
|
87
|
+
- <"수용 기준 품질 규칙" 표의 금지 패턴들>
|
|
88
|
+
- <사용자가 명시한 dry-run / touch 안 할 경로 등>
|
|
89
|
+
검증 방법:
|
|
90
|
+
- <각 AC 의 verification command (bash / curl / file check)>
|
|
91
|
+
컴파운드 패턴 (참고):
|
|
92
|
+
- <compound-search top 1-2 결과 — 본 작업 키워드로 검색>
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
2. 사용자에게 박스를 보여주고 안내:
|
|
96
|
+
```
|
|
97
|
+
GOAL 박제 완료. 다음 옵션:
|
|
98
|
+
- 이 박스를 다른 컨텍스트/에이전트에 위임 → 복사 사용
|
|
99
|
+
- 본 세션에서 자동 실행 → `forge-loop resume` 로 Phase 2 이어 실행
|
|
100
|
+
상태 파일: ~/.forgen/state/forge-loop.json (resume 시 재활용)
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
3. 종료. **Anti-Polite-Stop 규칙은 goal-only 모드에 적용 안 함** — 박제가 목적이고 실행은 명시적 escalation 시에만.
|
|
104
|
+
|
|
76
105
|
## Phase 2: 스토리 실행 루프
|
|
77
106
|
|
|
78
107
|
### 2-1. Compound-In (스토리별)
|
|
@@ -193,6 +222,52 @@ compound에 저장하시겠습니까? [Y/n]
|
|
|
193
222
|
<Arguments>
|
|
194
223
|
- `[task description]`: 실행할 작업 설명. 생략 시 현재 대화 컨텍스트에서 추론.
|
|
195
224
|
- `resume`: 이전에 중단된 루프를 재개합니다.
|
|
225
|
+
- `--goal-only` (또는 `--goal`, `--lock-only`): **goal-locking lightweight 모드**.
|
|
226
|
+
Phase 1 (PRD + 수용 기준 + 상태 파일 저장) 까지만 실행하고 Phase 2/3 (자동
|
|
227
|
+
실행 루프 + 최종 검증) 은 건너뜁니다. 산출물은 *구조화된 Goal 박스* — 작업
|
|
228
|
+
범위 / 완료 기준 / 제약 / 검증 방법을 한 markdown 으로 박제. 사용자가 다른
|
|
229
|
+
컨텍스트나 에이전트에 그대로 붙여 위임 가능. 추후 `forge-loop resume` 로
|
|
230
|
+
자동 실행 사이클 escalate 가능 (상태 파일 재활용).
|
|
231
|
+
|
|
232
|
+
goal-only 모드의 산출물 포맷:
|
|
233
|
+
```
|
|
234
|
+
GOAL: <한 문장 요약>
|
|
235
|
+
완료 기준 (Acceptance Criteria — 증거 타입 포함):
|
|
236
|
+
- [ ] AC1: <테스트 로그 / 파일 변경 / dry-run 출력>
|
|
237
|
+
- [ ] AC2: ...
|
|
238
|
+
제약 (Out-of-Scope / 안 할 것):
|
|
239
|
+
- <실 발송·배포·삭제 금지 / dry-run 한정>
|
|
240
|
+
- <touch 안 할 경로>
|
|
241
|
+
검증 방법:
|
|
242
|
+
- <bash 명령 / 파일 확인 / 외부 verification>
|
|
243
|
+
컴파운드 패턴 (참고):
|
|
244
|
+
- <compound-search 결과 top 1-2>
|
|
245
|
+
```
|
|
246
|
+
|
|
247
|
+
goal-only 모드는 stop-guard 의 fact-vs-agreement / self-score-inflation
|
|
248
|
+
체크와 직접 연동 — Goal 박스 박제 후 응답이 "완료" 주장 시 AC 의 증거가
|
|
249
|
+
포함되어야 통과.
|
|
196
250
|
</Arguments>
|
|
197
251
|
|
|
198
252
|
$ARGUMENTS
|
|
253
|
+
|
|
254
|
+
---
|
|
255
|
+
|
|
256
|
+
## `--with-codex` flag (cross-model review)
|
|
257
|
+
|
|
258
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
259
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
260
|
+
|
|
261
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
262
|
+
2. Invoke codex via Bash:
|
|
263
|
+
```bash
|
|
264
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
265
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
266
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
267
|
+
```
|
|
268
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
269
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
270
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
271
|
+
|
|
272
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
273
|
+
|
package/skills/learn/SKILL.md
CHANGED
|
@@ -214,3 +214,24 @@ PRUNE CANDIDATES / 정리 후보
|
|
|
214
214
|
</Arguments>
|
|
215
215
|
|
|
216
216
|
$ARGUMENTS
|
|
217
|
+
|
|
218
|
+
---
|
|
219
|
+
|
|
220
|
+
## `--with-codex` flag (cross-model review)
|
|
221
|
+
|
|
222
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
223
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
224
|
+
|
|
225
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
226
|
+
2. Invoke codex via Bash:
|
|
227
|
+
```bash
|
|
228
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
229
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
230
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
231
|
+
```
|
|
232
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
233
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
234
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
235
|
+
|
|
236
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
237
|
+
|
package/skills/retro/SKILL.md
CHANGED
|
@@ -197,3 +197,24 @@ RECOMMENDATIONS
|
|
|
197
197
|
</Arguments>
|
|
198
198
|
|
|
199
199
|
$ARGUMENTS
|
|
200
|
+
|
|
201
|
+
---
|
|
202
|
+
|
|
203
|
+
## `--with-codex` flag (cross-model review)
|
|
204
|
+
|
|
205
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
206
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
207
|
+
|
|
208
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
209
|
+
2. Invoke codex via Bash:
|
|
210
|
+
```bash
|
|
211
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
212
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
213
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
214
|
+
```
|
|
215
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
216
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
217
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
218
|
+
|
|
219
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
220
|
+
|
package/skills/ship/SKILL.md
CHANGED
|
@@ -257,3 +257,24 @@ Action: {다음 행동}
|
|
|
257
257
|
</Arguments>
|
|
258
258
|
|
|
259
259
|
$ARGUMENTS
|
|
260
|
+
|
|
261
|
+
---
|
|
262
|
+
|
|
263
|
+
## `--with-codex` flag (cross-model review)
|
|
264
|
+
|
|
265
|
+
If `$ARGUMENTS` contains any of `--with-codex`, `--코덱스`, `with codex`, `코덱스 검토`, `코덱스로 검토`,
|
|
266
|
+
then after completing the primary skill work, perform a cross-model review pass:
|
|
267
|
+
|
|
268
|
+
1. Save your primary output text to a temp file (e.g., `/tmp/forgen-with-codex-$(date +%s).md`).
|
|
269
|
+
2. Invoke codex via Bash:
|
|
270
|
+
```bash
|
|
271
|
+
codex exec --json --ignore-user-config --ignore-rules --ephemeral \
|
|
272
|
+
-s read-only -c approval_policy="never" --skip-git-repo-check \
|
|
273
|
+
"$(printf 'You are a second-opinion reviewer for another AI assistant\\u0027s output. Read the work product below and report ONLY:\n1. Defects, gaps, or risks the original work missed\n2. Specific disagreements with the original\n3. Topics that should have been covered but were not\n\nOutput format: prioritized bullet list (max 15 items, severity-sorted, no prose intro). If you find nothing material, say "No critical issues found."\n\n<work>\n%s\n</work>' "$(cat /tmp/forgen-with-codex-*.md)")"
|
|
274
|
+
```
|
|
275
|
+
3. Append the codex output under heading `## Codex Cross-Review (--with-codex)` in your final response.
|
|
276
|
+
4. If codex flags critical issues, briefly acknowledge + suggest follow-up.
|
|
277
|
+
5. If `codex: command not found`, note in response and skip the review pass (do not fail).
|
|
278
|
+
|
|
279
|
+
OPT-IN per invocation. Without the flag, skip this entire section.
|
|
280
|
+
|