@guidobuilds/forge-ai 0.3.0 → 0.5.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.
- package/CHANGELOG.md +47 -0
- package/README.md +119 -2
- package/artifacts/forge/forge.md +14 -1
- package/artifacts/forge-adversary/forge-adversary.md +122 -0
- package/artifacts/forge-grill/forge-grill.md +2 -1
- package/artifacts/forge-worker/forge-worker.md +109 -4
- package/artifacts/using-forge/using-forge.md +69 -2
- package/dist/src/adapters/grok-known.js +37 -0
- package/dist/src/adapters/grok.js +41 -0
- package/dist/src/cli.js +147 -91
- package/dist/src/model.js +1 -1
- package/dist/src/paths.js +4 -0
- package/dist/src/processor.js +13 -5
- package/dist/src/self-update.js +70 -0
- package/dist/src/version-check.js +75 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -9,6 +9,53 @@ Versions prior to 0.3.0 are not reconstructed here; see git history for earlier
|
|
|
9
9
|
|
|
10
10
|
## [Unreleased]
|
|
11
11
|
|
|
12
|
+
## [0.5.0] - 2026-06-20
|
|
13
|
+
|
|
14
|
+
### Added
|
|
15
|
+
|
|
16
|
+
- **Grok Build (`--platform grok`) as a first-class target.** `forge`, `forge-grill`, and `using-forge` install as Grok skills under `.grok/skills/<name>/SKILL.md`; `forge-worker` and `forge-adversary` install as Grok subagents under `.grok/agents/<name>.md`. Grok's built-in tool IDs (`run_terminal_cmd`, `grep_search`, `search_replace`, etc.) are used in the worker and adversary toolsets, replacing the Claude-specific names. Included in `--platform all`. Grok Build v0.2.56+ required.
|
|
17
|
+
|
|
18
|
+
### Changed
|
|
19
|
+
|
|
20
|
+
- **Orchestrator route announcement**: before the first dispatch, the orchestrator now states the chosen route to the user — work types joined by arrows (e.g. `build -> verify`, `inspect -> build -> verify`, `inspect -> design -> plan -> build -> verify`), whether a `forge-grill` pass runs before build and an independent verify or `forge-adversary` gate runs after, and one clause on why it is the lightest safe route. Re-announced only when the route changes materially mid-flight.
|
|
21
|
+
- **Proactive `forge-grill`**: the orchestrator now runs `forge-grill` proactively before build for non-trivial, risk-bearing, or multi-step work with unresolved assumptions. Previously grill was effectively opt-in (user-triggered via `/forge-grill`). Trivial, surgical, and read-only work still skips grill.
|
|
22
|
+
|
|
23
|
+
### Migration from 0.4.0
|
|
24
|
+
|
|
25
|
+
- Run `npx @guidobuilds/forge-ai update` to add the new `forge-grill` and `using-forge` prompt changes and the Grok Build artifacts. No breaking changes to the CLI, state files, or existing Claude/OpenCode/Codex installs.
|
|
26
|
+
|
|
27
|
+
## [0.4.0] - 2026-06-16
|
|
28
|
+
|
|
29
|
+
### Added
|
|
30
|
+
|
|
31
|
+
- **Adaptive `.forge/<feature-slug>/` state model** for the orchestration harness, sized to task complexity. Trivial work stays on the `build -> verify` path with no artifacts; non-trivial or multi-session work gains a structured state ledger. Documented in `using-forge` (routing tiers + triggers) and `forge-worker` (schema + templates). No distribution-engine change — the state files are runtime-generated by the worker.
|
|
32
|
+
- **`feature-list.json` feature-list primitive**: the unit-of-work ledger where each feature carries the triple `behavior` + `verification` (a runnable command) + `state` (`not_started | active | blocked | passing`), plus `evidence` and `dependencies`.
|
|
33
|
+
- **Definition of Done with verification-evidence gating**: a feature reaches `passing` only after its verification command was actually run and recorded in `verification.md`; never on assertion alone.
|
|
34
|
+
- **Independent verification**: for non-trivial work the builder may not self-certify; the orchestrator dispatches a separate `forge-worker` verify run that re-runs the checks and flips state.
|
|
35
|
+
- **`forge-adversary` agent — dedicated post-build red-team gate.** A new subagent (`kind: agent`; OpenCode subagent, Claude agent) the orchestrator dispatches *after* build to break a worker's output across four lenses (logical/requirements, technical/runtime, security, performance/scale). It writes reproductions under `.forge/<slug>/adversary/`, records every attempt in `verification.md`, and gates the Definition of Done — a confirmed, reproducible break moves the feature to `blocked`; it never edits the implementation under test. Reports `WORK_TYPE: verify`, so the worker contract is unchanged. Complements `forge-grill` (which grills plans/designs *before* build). `forge`, `using-forge`, and `forge-worker` updated to dispatch it for risk-bearing work.
|
|
36
|
+
- **Persisted handoff/progress**: `progress.md` and `session-handoff.md` templates for cross-session continuity, created adaptively when work spans sessions or blocks.
|
|
37
|
+
- `forge-ai self-update` command. Detects how the CLI is installed (pnpm global, npm global, Homebrew npm, npx, or unknown) and runs the right update command with the right flags (`--prefer-online` for pnpm to sidestep its metadata cache). After updating the binary it automatically runs `forge-ai update` to refresh the spec kit. Flags: `--to <version>` to pin a specific version, `--dry-run` to preview, `--skip-spec-update` to only bump the CLI.
|
|
38
|
+
- Background version check on every interactive run. Calls the npm registry (with 1.5s timeout, cached for 1h at `~/.forge-ai/version-check.json`) and prints `forge-ai vX.Y.Z (vA.B.C available — run \`forge-ai self-update\` to upgrade)` when a newer version exists. Silent on failure; never blocks the command.
|
|
39
|
+
- `--no-update-check` CLI flag and `FORGE_NO_UPDATE_CHECK=1` env var to opt out of the version check. Also auto-skipped in CI (`CI=true`) and non-interactive runs.
|
|
40
|
+
- README "How to Use" section explaining how to invoke Forge per platform: `/forge` skill on Claude Code (with `forge-worker` as a delegated subagent), `forge` primary agent on OpenCode, and the partial `.toml` agents on Codex — including the Claude advisory-vs-OpenCode-enforced trade-off.
|
|
41
|
+
- **Feedback ratchet — `.forge/lessons.md`**: a project-scoped, topic-keyed lessons file the worker proactively appends to after each run (decision / non-obvious fix / convention / failure). Reusing a topic-key updates an existing lesson instead of creating a contradictory duplicate, so the harness compounds across sessions instead of repeating mistakes.
|
|
42
|
+
- **Bootstrap repo-facts — `.forge/repo-facts.md`**: a one-time `inspect`-written standing spec (stack, build/test/lint commands, conventions, hard constraints) the worker rereads each dispatch, paying the intent/reconstruction cost once.
|
|
43
|
+
- **Closure + cross-task index — `.forge/index.md` and `.forge/_archive/`**: on `passing`, the verify dispatch flushes lessons and appends a one-line ledger entry; completed slugs may be archived. Each feature carries a falsifiable `archiveWhen` condition set at creation.
|
|
44
|
+
- **Effort routing**: the orchestrator now states an effort level per worker dispatch (low for `inspect`/`verify`/`operate`/routine `build`, medium for most `build`/`plan`, high for `design`/synthesis/novel work) — match effort to difficulty rather than defaulting high.
|
|
45
|
+
- **Inline-vs-delegate threshold**: the orchestrator handles inline only a 1-3 file read / mechanical write / git status, and delegates at 4+ files, multi-file writes, or running tests/builds/installs — keeping the thread thin (summaries, not implementations).
|
|
46
|
+
- **Optional hooks pack** (README): an opt-in Claude Code `settings.json` snippet (Stop + PostToolUse) to *enforce* the verification gate mechanically for unattended runs — kept thin and optional, since strong models honor the gate from the operating model alone.
|
|
47
|
+
- **Harness-content validation**: `validate`/`install` emit a `BODY_OVER_BUDGET` info diagnostic when an artifact body exceeds its soft line budget (keep always-loaded files small). Never an error; does not block installs.
|
|
48
|
+
|
|
49
|
+
### Changed
|
|
50
|
+
|
|
51
|
+
- **Independent verification is now adversarial.** The separate `forge-worker` verify dispatch tries to *disprove* "done" rather than confirm it: it refutes risk-bearing features across up to three distinct lenses and keeps `passing` only if at least two fail to refute; confirms the check was not weakened, deleted, skipped, or stubbed and that its output exercises the named `behavior`; logs refuted/uncertain candidates instead of dropping them silently; and escalates instead of looping when the same failure recurs. The Definition of Done in `using-forge` and the verify/build modes in `forge-worker` are updated to match; `feature-list.json` gains an `archiveWhen` field.
|
|
52
|
+
|
|
53
|
+
### Migration from 0.3.0
|
|
54
|
+
|
|
55
|
+
- Run `npx @guidobuilds/forge-ai update` (not `install`) to add the new `forge-adversary` agent and refresh the `forge`, `using-forge`, and `forge-worker` artifacts to the adversarial-verification operating model. Local edits to managed files are backed up automatically to `~/.forge-ai/backups/`.
|
|
56
|
+
- No breaking changes to the CLI or distribution layout. The `.forge/<feature-slug>/` state files (`feature-list.json`, `verification.md`, `lessons.md`, `repo-facts.md`, `index.md`, handoff/progress) are runtime-generated by the worker — nothing to migrate by hand.
|
|
57
|
+
- If you installed the CLI globally, `forge-ai self-update` (new in 0.4.0) bumps the binary and then refreshes the spec kit for you.
|
|
58
|
+
|
|
12
59
|
## [0.3.0] - 2026-05-15
|
|
13
60
|
|
|
14
61
|
### Added
|
package/README.md
CHANGED
|
@@ -49,6 +49,8 @@ build -> verify
|
|
|
49
49
|
|
|
50
50
|
There is no mandatory lifecycle. Forge tries to choose the lightest safe path based on the task, risk, and available context.
|
|
51
51
|
|
|
52
|
+
Before delegating, the orchestrator states the chosen route to the user — the work types it plans to run, whether `forge-grill` runs before build, and why it is the lightest safe path for that request.
|
|
53
|
+
|
|
52
54
|
## Durable Context
|
|
53
55
|
|
|
54
56
|
When a task benefits from persistent context, Forge writes notes under `.forge/<feature-slug>/`.
|
|
@@ -62,6 +64,21 @@ These notes are useful for:
|
|
|
62
64
|
|
|
63
65
|
Small, obvious changes do not need ceremony. The goal is to use durable artifacts only when they reduce ambiguity or risk.
|
|
64
66
|
|
|
67
|
+
### State model for non-trivial work
|
|
68
|
+
|
|
69
|
+
For non-trivial or multi-session work, Forge keeps a small state model under `.forge/<feature-slug>/`, sized to the task:
|
|
70
|
+
|
|
71
|
+
- `feature-list.json` — the unit-of-work ledger. Each feature carries the triple `behavior` + `verification` (a runnable command) + `state` (`not_started | active | blocked | passing`).
|
|
72
|
+
- `verification.md` — recorded verification evidence: the command, its output, and a pass/fail verdict.
|
|
73
|
+
- `progress.md` / `session-handoff.md` — session continuity and handoff, written when work spans sessions or blocks.
|
|
74
|
+
|
|
75
|
+
Two rules make "done" mean done:
|
|
76
|
+
|
|
77
|
+
- **Definition of Done.** A feature only reaches `passing` once its verification command was actually run and the evidence is recorded in `verification.md`. No feature is marked done on assertion alone.
|
|
78
|
+
- **Independent verification.** For non-trivial work the builder does not certify its own work. The orchestrator dispatches a separate `forge-worker` verify run that re-runs the checks and flips the state.
|
|
79
|
+
|
|
80
|
+
Trivial, surgical changes skip all of this and stay on the `build -> verify` path.
|
|
81
|
+
|
|
65
82
|
## Supported Agents
|
|
66
83
|
|
|
67
84
|
Forge currently installs support for:
|
|
@@ -69,6 +86,7 @@ Forge currently installs support for:
|
|
|
69
86
|
- OpenCode
|
|
70
87
|
- Codex
|
|
71
88
|
- Claude Code
|
|
89
|
+
- Grok Build
|
|
72
90
|
|
|
73
91
|
The same operating model is shared across all supported agents so the workflow stays mostly consistent even when the underlying tool changes.
|
|
74
92
|
|
|
@@ -106,6 +124,95 @@ Validate a local Forge source tree:
|
|
|
106
124
|
npx @guidobuilds/forge-ai validate --source .
|
|
107
125
|
```
|
|
108
126
|
|
|
127
|
+
## How to Use
|
|
128
|
+
|
|
129
|
+
Forge installs the **same operating model** on every agent, but **how you invoke it differs per platform**, because each agent exposes different primitives (skills, subagents, agent switching). The installer is only step one — this section is how you actually drive Forge once it is installed.
|
|
130
|
+
|
|
131
|
+
### The pieces
|
|
132
|
+
|
|
133
|
+
Forge is one orchestrator, a universal worker, and a dedicated adversary, with two supporting skills:
|
|
134
|
+
|
|
135
|
+
- **`forge`** — the orchestrator. It talks to you, decides how much process a task needs, and delegates the real work. It does not edit code itself.
|
|
136
|
+
- **`forge-worker`** — the worker. It does the inspect / design / plan / build / operate / verify work in its own context and reports back. This is what keeps the orchestrator's context clean.
|
|
137
|
+
- **`forge-adversary`** — the breaker. After a build, the orchestrator dispatches it to *try to break* the work — logically and technically (logic/requirements, runtime, security, performance). It gates the Definition of Done: a confirmed, reproducible break keeps the feature out of `passing`. It complements `forge-grill`, which grills plans *before* building.
|
|
138
|
+
- **`using-forge`** — the shared operating-model skill the orchestrator follows.
|
|
139
|
+
- **`forge-grill`** — an orchestrator mode for stress-testing a plan or design before building. The orchestrator invokes it proactively before non-trivial or risk-bearing builds; also available as `/forge-grill` for manual use.
|
|
140
|
+
|
|
141
|
+
What changes per platform is the **kind** each piece is installed as, and therefore how you trigger it.
|
|
142
|
+
|
|
143
|
+
### Claude Code
|
|
144
|
+
|
|
145
|
+
| Piece | Installed as | How you invoke it |
|
|
146
|
+
|---|---|---|
|
|
147
|
+
| `forge` | skill | type `/forge` in the prompt |
|
|
148
|
+
| `forge-grill` | skill | type `/forge-grill` |
|
|
149
|
+
| `using-forge` | skill | `/using-forge` (usually pulled in by `/forge`) |
|
|
150
|
+
| `forge-worker` | subagent | the main thread delegates to it; or say "use the forge-worker subagent" |
|
|
151
|
+
| `forge-adversary` | subagent | the orchestrator delegates to it after build to gate risk-bearing work |
|
|
152
|
+
|
|
153
|
+
Start a session by typing **`/forge`**. That loads the orchestrator role into your main Claude Code thread, which then delegates each bounded task to the `forge-worker` subagent (via the Task tool), keeping your main conversation thin.
|
|
154
|
+
|
|
155
|
+
> Why a skill and not an agent on Claude? A Claude Code subagent cannot itself spawn subagents (it has no Task tool), so the orchestrator has to live in the main thread — and the way you inject behavior into the main thread is a skill. The trade-off: the "delegate, never do worker work inline" discipline is followed by instruction, not enforced by tool restrictions, because a skill cannot remove tools from the main thread.
|
|
156
|
+
|
|
157
|
+
### OpenCode
|
|
158
|
+
|
|
159
|
+
| Piece | Installed as | How you invoke it |
|
|
160
|
+
|---|---|---|
|
|
161
|
+
| `forge` | primary agent | switch your active agent to `forge` |
|
|
162
|
+
| `forge-worker` | subagent | the `forge` agent delegates to it |
|
|
163
|
+
| `forge-adversary` | subagent | the `forge` agent delegates to it to gate risk-bearing work after build |
|
|
164
|
+
| `using-forge`, `forge-grill` | skills | loaded by the agent as needed |
|
|
165
|
+
|
|
166
|
+
Switch your primary agent to **`forge`**. Unlike Claude Code, the orchestrator here is a real agent with file and shell tools **denied**, so it is *structurally* forced to delegate to the `forge-worker` subagent instead of doing the work itself.
|
|
167
|
+
|
|
168
|
+
### Codex
|
|
169
|
+
|
|
170
|
+
| Piece | Installed as | Location |
|
|
171
|
+
|---|---|---|
|
|
172
|
+
| `forge`, `forge-worker`, `forge-adversary` | agents (`.toml`) | `~/.codex/agents/` (or `.codex/agents/` per project) |
|
|
173
|
+
| `using-forge`, `forge-grill` | skills | `~/.agents/skills/` (or `.agents/skills/` per project) |
|
|
174
|
+
|
|
175
|
+
Codex support is the most partial of the three: Forge writes the agent `.toml` files but does not generate `AGENTS.md` or profiles, so wiring them into a Codex run may take manual steps. Treat Codex support as experimental.
|
|
176
|
+
|
|
177
|
+
### Project vs user scope
|
|
178
|
+
|
|
179
|
+
### Grok Build
|
|
180
|
+
|
|
181
|
+
| Piece | Installed as | How you invoke it |
|
|
182
|
+
|---|---|---|
|
|
183
|
+
| `forge` | skill | type `/forge` in the prompt |
|
|
184
|
+
| `forge-grill` | skill | type `/forge-grill` |
|
|
185
|
+
| `using-forge` | skill | `/using-forge` (usually pulled in by `/forge`) |
|
|
186
|
+
| `forge-worker` | subagent | the main thread delegates to it via the `task` tool |
|
|
187
|
+
| `forge-adversary` | subagent | the orchestrator delegates to it after build to gate risk-bearing work |
|
|
188
|
+
|
|
189
|
+
Start a session by typing **`/forge`**. Like Claude Code, the orchestrator runs as a skill in the main Grok session, which then delegates bounded work to the `forge-worker` subagent. Grok uses its own tool IDs (`run_terminal_cmd`, `grep_search`, `search_replace`, etc.) — the installer translates the worker's toolset automatically.
|
|
190
|
+
|
|
191
|
+
> **Note:** Grok Build already auto-discovers skills and agents from `~/.claude/` for compatibility. If you have a Claude Code install, Grok may partially pick up those files — but with Claude tool names that Grok doesn't recognize. A native Grok install (`--platform grok`) writes `.grok/`-scoped files with the correct Grok tool IDs.
|
|
192
|
+
|
|
193
|
+
### Project vs user scope
|
|
194
|
+
|
|
195
|
+
With `--scope user` (the default) the definitions live under your home directory and apply everywhere. With `--scope project` they live in the repo (`.claude/`, `.opencode/`, `.codex/`, `.agents/`, `.grok/`) and apply only there. Invocation is identical either way.
|
|
196
|
+
|
|
197
|
+
## Optional: enforce the gate with hooks (Claude Code)
|
|
198
|
+
|
|
199
|
+
Forge's Definition of Done is followed by instruction, not enforced — strong models honor the gate from the operating model alone. If you want the verification gate enforced *mechanically* on Claude Code (e.g. for unattended runs), add an opt-in hook to your `.claude/settings.json`. Keep it thin: a safety net for the one invariant that must hold, not a compliance layer.
|
|
200
|
+
|
|
201
|
+
```json
|
|
202
|
+
{
|
|
203
|
+
"hooks": {
|
|
204
|
+
"Stop": [
|
|
205
|
+
{ "hooks": [ { "type": "command", "command": "<your project's verification command, e.g. pnpm test --silent>" } ] }
|
|
206
|
+
],
|
|
207
|
+
"PostToolUse": [
|
|
208
|
+
{ "matcher": "Write|Edit", "hooks": [ { "type": "command", "command": "<your fast type/lint check, e.g. pnpm typecheck>" } ] }
|
|
209
|
+
]
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
The **Stop** hook re-runs your checks when the agent tries to finish, so a failing gate blocks a premature "done"; the **PostToolUse** hook surfaces type/lint errors after each edit for mid-task self-correction. Point the Stop hook at fast unit checks and leave slow suites to CI. This is intentionally optional — reach for it only when you want the gate enforced without you in the room.
|
|
215
|
+
|
|
109
216
|
## Local Development
|
|
110
217
|
|
|
111
218
|
Forge uses [pnpm](https://pnpm.io) for development (pinned via `packageManager` in `package.json`, so `corepack enable` is enough — no global install needed). The published package is still consumed by end users via `npx`/npm, unchanged.
|
|
@@ -126,10 +233,20 @@ node bin/forge-ai.mjs install --source . --platform all --scope project --dry-ru
|
|
|
126
233
|
|
|
127
234
|
## Updating
|
|
128
235
|
|
|
129
|
-
|
|
236
|
+
If you have Forge installed globally, the simplest way is:
|
|
130
237
|
|
|
131
238
|
```sh
|
|
132
|
-
|
|
239
|
+
forge-ai self-update
|
|
240
|
+
```
|
|
241
|
+
|
|
242
|
+
This detects how the CLI was installed (pnpm global, npm global, Homebrew npm, etc.) and runs the right upgrade command — including the `--prefer-online` flag that sidesteps pnpm's metadata cache when a new version was just published. After bumping the binary, it automatically runs `forge-ai update` to refresh the spec kit.
|
|
243
|
+
|
|
244
|
+
Forge also pings the registry on every interactive run and prints a one-line notice when a newer version is available, so you don't have to remember to check.
|
|
245
|
+
|
|
246
|
+
If you don't have a global install (running via `npx`):
|
|
247
|
+
|
|
248
|
+
```sh
|
|
249
|
+
npx @guidobuilds/forge-ai@latest update
|
|
133
250
|
```
|
|
134
251
|
|
|
135
252
|
Forge replaces its managed agent and skill definitions in your supported agent configuration directories.
|
package/artifacts/forge/forge.md
CHANGED
|
@@ -4,6 +4,8 @@ description: Forge orchestrator with dynamic runtime routing and a single worker
|
|
|
4
4
|
kind: agent
|
|
5
5
|
claude:
|
|
6
6
|
kind: skill
|
|
7
|
+
grok:
|
|
8
|
+
kind: skill
|
|
7
9
|
opencode:
|
|
8
10
|
mode: primary
|
|
9
11
|
permissions:
|
|
@@ -37,15 +39,26 @@ The `using-forge` skill owns runtime routing, operating principles, approval heu
|
|
|
37
39
|
- Delegate all technical and operational work to Forge workers.
|
|
38
40
|
- Keep one thin thread with the user.
|
|
39
41
|
- Choose the lightest safe routing permitted by the skill.
|
|
42
|
+
- Before the first dispatch, state the chosen route to the user (see `using-forge`: Route announcement).
|
|
43
|
+
- Run `forge-grill` proactively before building non-trivial or risk-bearing work; do not wait for the user to ask (see `using-forge`: Routing rules).
|
|
40
44
|
- Enforce the Forge worker contract strictly.
|
|
45
|
+
- Assign an effort level per dispatch and delegate by size (see `using-forge`: Effort routing, Routing rules).
|
|
41
46
|
|
|
42
47
|
## Worker model
|
|
43
|
-
- `forge-worker` is the only worker type
|
|
48
|
+
- `forge-worker` is the only universal worker type; route all build and operational work to it.
|
|
49
|
+
- `forge-adversary` is a dedicated adversarial verification agent: dispatch it as the Definition-of-Done gate for risk-bearing work to break the build before it can reach `passing`.
|
|
44
50
|
- You may launch one worker instance for a bounded task.
|
|
45
51
|
- You may launch multiple `forge-worker` instances in sequence when one result should shape the next delegation.
|
|
46
52
|
- You may launch multiple `forge-worker` instances in parallel when subgoals are sufficiently independent.
|
|
47
53
|
- Keep each worker invocation narrowly scoped so multiple instances do not collide on the same ownership or files unless deliberate.
|
|
48
54
|
|
|
55
|
+
## State model
|
|
56
|
+
- Size the state model to the work. Keep trivial, surgical changes light: route `build -> verify` with no state artifacts.
|
|
57
|
+
- For non-trivial or multi-session work, route through the `.forge/<feature-slug>/` state model defined in `using-forge`: maintain `feature-list.json` (behavior + verification + state) and persist `progress.md` / `session-handoff.md` when work spans sessions or blocks.
|
|
58
|
+
- A feature reaches `passing` only via recorded verification evidence (the Definition of Done in `using-forge`).
|
|
59
|
+
- For non-trivial work, dispatch a separate verify run; never accept a builder's self-certified `passing`. Prefer `forge-adversary` for risk-bearing work and a `forge-worker` verify run otherwise — both must be a different instance than the builder.
|
|
60
|
+
- Read `.forge/repo-facts.md` and `.forge/lessons.md` when present, and have the verify dispatch flush lessons and update `.forge/index.md` at closure (see `using-forge`).
|
|
61
|
+
|
|
49
62
|
## Contract enforcement
|
|
50
63
|
Each worker response must include:
|
|
51
64
|
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: forge-adversary
|
|
3
|
+
description: Forge adversarial breaker — attacks a worker's completed work logically and technically and gates `passing` on recorded evidence.
|
|
4
|
+
kind: agent
|
|
5
|
+
claude:
|
|
6
|
+
permissions:
|
|
7
|
+
tools: [TodoWrite, Read, Write, Edit, Bash, Glob, Grep, LS, MultiEdit, WebFetch]
|
|
8
|
+
grok:
|
|
9
|
+
permissions:
|
|
10
|
+
tools: [todo_write, read_file, search_replace, run_terminal_cmd, grep_search, list_dir, web_fetch]
|
|
11
|
+
opencode:
|
|
12
|
+
mode: subagent
|
|
13
|
+
permissions:
|
|
14
|
+
todowrite: allow
|
|
15
|
+
read: allow
|
|
16
|
+
write: allow
|
|
17
|
+
edit: allow
|
|
18
|
+
bash: allow
|
|
19
|
+
glob: allow
|
|
20
|
+
grep: allow
|
|
21
|
+
list: allow
|
|
22
|
+
patch: allow
|
|
23
|
+
skill: allow
|
|
24
|
+
webfetch: allow
|
|
25
|
+
---
|
|
26
|
+
|
|
27
|
+
# Forge Adversary
|
|
28
|
+
|
|
29
|
+
## Role
|
|
30
|
+
|
|
31
|
+
You are the Forge adversary: an independent red-team agent dispatched *after* a `forge-worker` has produced or changed work. Your job is to **break it** — logically and technically — not to confirm it. You did not build it, so you owe it no benefit of the doubt.
|
|
32
|
+
|
|
33
|
+
You are the gate. A feature does not reach `passing` until you **fail** to break it with recorded evidence.
|
|
34
|
+
|
|
35
|
+
You are distinct from the two existing adversarial mechanisms:
|
|
36
|
+
- `forge-grill` grills *plans and designs before* build. You attack *built* work.
|
|
37
|
+
- The universal `forge-worker` verify mode is a general check. You are the dedicated, specialized verify/break gate the orchestrator dispatches for risk-bearing work.
|
|
38
|
+
|
|
39
|
+
## Inputs
|
|
40
|
+
|
|
41
|
+
- Orchestrator prompt naming the `feature-slug` under attack, the requirement / acceptance criteria, the effort level, and what is out of scope
|
|
42
|
+
- The artifacts the worker produced: code, files, and `.forge/<feature-slug>/` state
|
|
43
|
+
- The `verification` command(s) and the relevant `feature-list.json` entries
|
|
44
|
+
- Optional: `.forge/<feature-slug>/verification.md`, `design.md`, `plan.md`, `build-log.md`
|
|
45
|
+
- Optional: `.forge/repo-facts.md` and `.forge/lessons.md`
|
|
46
|
+
|
|
47
|
+
When state-model files exist, read them before acting and treat `feature-list.json` as the source of truth for what is in scope and its current state. When `.forge/repo-facts.md` or `.forge/lessons.md` exist, read them first so you reuse known facts and known weaknesses.
|
|
48
|
+
|
|
49
|
+
## Core rules
|
|
50
|
+
|
|
51
|
+
- **Independence**: you are a different instance than the builder. Never accept a self-certified `passing`.
|
|
52
|
+
- **Attack, do not repair**: you may write reproductions (failing tests, fuzz scripts, payloads) and state files, but you must NOT edit the implementation under test. Surface the breakage and leave the fix to a build dispatch.
|
|
53
|
+
- **Evidence over assertion**: every claimed break must be reproducible — a command plus the observed failure — and recorded in `verification.md`. No break is real on assertion alone.
|
|
54
|
+
- **Strict judging**: a break counts only if it violates a stated requirement or an invariant a reasonable user expects. Separate real defects from style nits and speculation.
|
|
55
|
+
- **Minimum noise**: report the highest-severity, reproducible breaks first. Do not pad the report to look thorough.
|
|
56
|
+
- **Honor the effort level** stated in the dispatch; escalate only when the surface warrants it.
|
|
57
|
+
|
|
58
|
+
## Attack lenses
|
|
59
|
+
|
|
60
|
+
Run the lenses that fit the target. For risk-bearing work cover at least Logical and Technical, then add Security and Performance as the surface warrants.
|
|
61
|
+
|
|
62
|
+
### Logical / requirements
|
|
63
|
+
|
|
64
|
+
- Map each stated requirement / acceptance criterion to concrete evidence it is met; flag gaps and over-delivery (scope creep).
|
|
65
|
+
- Hunt contradictions, ambiguous acceptance criteria, and behaviors the build assumes but never states.
|
|
66
|
+
- Enumerate edge cases the build ignores: empty, boundary, ordering, idempotency, repeated invocation, and concurrent intent.
|
|
67
|
+
|
|
68
|
+
### Technical / runtime
|
|
69
|
+
|
|
70
|
+
- Run the existing suite first; then craft adversarial inputs: empty, boundary, malformed, oversized, unexpected types and encodings.
|
|
71
|
+
- Probe error handling and silent failures, invalid or partial states, and resource cleanup.
|
|
72
|
+
- Check for regressions in adjacent behavior the change could disturb.
|
|
73
|
+
- Write a failing reproduction test for each confirmed defect.
|
|
74
|
+
|
|
75
|
+
### Security
|
|
76
|
+
|
|
77
|
+
In scope only when the change crosses a trust boundary. Probe injection (SQL / command / path / template), input validation and sanitization, authz/authn bypass, secret and credential exposure, unsafe deserialization, and SSRF.
|
|
78
|
+
|
|
79
|
+
### Performance / scale
|
|
80
|
+
|
|
81
|
+
In scope only when the work has a load or scale dimension. Probe algorithmic complexity, degenerate and large-volume inputs, unbounded growth, N+1 or repeated work, and resource limits.
|
|
82
|
+
|
|
83
|
+
## Gate authority
|
|
84
|
+
|
|
85
|
+
You are the Definition-of-Done gate for the targeted feature(s), per the rules in `using-forge`.
|
|
86
|
+
|
|
87
|
+
- For each targeted feature in `feature-list.json`, run its `verification` command AND your adversarial attacks.
|
|
88
|
+
- A confirmed, reproducible break moves the feature to `blocked` with a one-line reason and an `evidence` pointer.
|
|
89
|
+
- For risk-bearing features, refute across up to three distinct lenses; keep `passing` only if at least two lenses fail to refute.
|
|
90
|
+
- Record EVERY attempt — confirmed, refuted, and uncertain — in `verification.md` (command + output excerpt + verdict + timestamp).
|
|
91
|
+
- Move a feature to `passing` only when your attacks fail to break it AND the Definition of Done in `using-forge` holds. Never weaken, delete, skip, or stub a check to make it pass.
|
|
92
|
+
- You are not the builder: when you confirm breaks, set state, hand back, and recommend a build dispatch to fix. Do not fix it yourself.
|
|
93
|
+
|
|
94
|
+
## Artifacts
|
|
95
|
+
|
|
96
|
+
- Write reproductions under `.forge/<feature-slug>/adversary/` (failing tests, fuzz scripts, payloads, repro steps).
|
|
97
|
+
- Record outcomes in `.forge/<feature-slug>/verification.md` — the Definition of Done store defined by `using-forge`.
|
|
98
|
+
- Update `state` and `evidence` in `feature-list.json` only for the features you targeted.
|
|
99
|
+
- At closure, flush durable lessons from confirmed breaks to `.forge/lessons.md` and append a line to `.forge/index.md`.
|
|
100
|
+
|
|
101
|
+
## Contract (strict)
|
|
102
|
+
|
|
103
|
+
Return exactly the Forge worker contract. Report `WORK_TYPE: verify` — you are the specialized verify dispatch, so the shared contract and work types stay unchanged.
|
|
104
|
+
|
|
105
|
+
```text
|
|
106
|
+
STATUS: success|partial|blocked
|
|
107
|
+
WORK_TYPE: verify
|
|
108
|
+
FEATURE_SLUG: <kebab-case>
|
|
109
|
+
ARTIFACTS:
|
|
110
|
+
- <path or None>
|
|
111
|
+
SUMMARY:
|
|
112
|
+
- <point>
|
|
113
|
+
NEXT_RECOMMENDED: inspect|design|plan|build|operate|verify|ask-user|none
|
|
114
|
+
RISKS:
|
|
115
|
+
- <risk or None>
|
|
116
|
+
QUESTIONS:
|
|
117
|
+
1) <question>
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
`STATUS: success` means you could not break it and it passed the Definition of Done. `STATUS: partial` or `blocked` means you confirmed at least one break; set the feature accordingly and recommend `build` to fix. Use `QUESTIONS` only when `STATUS: blocked` on a decision only the user can resolve.
|
|
121
|
+
|
|
122
|
+
If your own output is malformed, reformat once on the same task; if malformed again, stop with an actionable error.
|
|
@@ -8,13 +8,14 @@ kind: skill
|
|
|
8
8
|
|
|
9
9
|
## Role
|
|
10
10
|
|
|
11
|
-
Use this skill when the user wants Forge to stress-test, challenge, or "grill" a plan, design, proposal, or implementation approach.
|
|
11
|
+
Use this skill when the user wants Forge to stress-test, challenge, or "grill" a plan, design, proposal, or implementation approach — or when the orchestrator proactively decides to grill before build (non-trivial, risk-bearing, or multi-step work with unresolved assumptions; see `using-forge`: Routing rules).
|
|
12
12
|
|
|
13
13
|
You are still the Forge orchestrator: keep the user thread thin, delegate technical and operational work to `forge-worker`, and use the lightest safe workflow that reaches shared understanding.
|
|
14
14
|
|
|
15
15
|
## Core behavior
|
|
16
16
|
|
|
17
17
|
- Build a decision tree for the plan or design under review.
|
|
18
|
+
- If a `.forge/<feature-slug>/feature-list.json` exists, focus the decision tree on features that are not yet `passing`.
|
|
18
19
|
- Resolve dependencies between decisions in an order that prevents rework.
|
|
19
20
|
- Challenge assumptions, edge cases, scope boundaries, sequencing, risks, and validation strategy.
|
|
20
21
|
- Prefer shared understanding over volume: ask the fewest high-leverage questions that close the next meaningful branch.
|
|
@@ -5,6 +5,9 @@ kind: agent
|
|
|
5
5
|
claude:
|
|
6
6
|
permissions:
|
|
7
7
|
tools: [TodoWrite, Read, Write, Edit, Bash, Glob, Grep, LS, MultiEdit, WebFetch]
|
|
8
|
+
grok:
|
|
9
|
+
permissions:
|
|
10
|
+
tools: [todo_write, read_file, search_replace, run_terminal_cmd, grep_search, list_dir, web_fetch]
|
|
8
11
|
opencode:
|
|
9
12
|
mode: subagent
|
|
10
13
|
permissions:
|
|
@@ -28,7 +31,7 @@ Execute only the subgoal assigned by the Forge orchestrator.
|
|
|
28
31
|
|
|
29
32
|
You are a universal worker derived from Forge's existing explore, design, plan, build, and helper behaviors. Treat those as internal modes, not mandatory phases.
|
|
30
33
|
|
|
31
|
-
You are the only worker type in Forge
|
|
34
|
+
You are the only universal worker type in Forge; the orchestrator may launch multiple instances of you in parallel or sequence. The dedicated `forge-adversary` agent handles adversarial verification gating for risk-bearing work.
|
|
32
35
|
|
|
33
36
|
## Inputs
|
|
34
37
|
|
|
@@ -37,8 +40,16 @@ You are the only worker type in Forge. The orchestrator may launch multiple inst
|
|
|
37
40
|
- Optional: `.forge/<feature-slug>/design.md`
|
|
38
41
|
- Optional: `.forge/<feature-slug>/plan.md`
|
|
39
42
|
- Optional: `.forge/<feature-slug>/build-log.md`
|
|
43
|
+
- Optional: `.forge/<feature-slug>/feature-list.json`
|
|
44
|
+
- Optional: `.forge/<feature-slug>/verification.md`
|
|
45
|
+
- Optional: `.forge/<feature-slug>/progress.md`
|
|
46
|
+
- Optional: `.forge/<feature-slug>/session-handoff.md`
|
|
47
|
+
- Optional: `.forge/repo-facts.md` — project-scoped stack, commands, conventions, and hard constraints
|
|
48
|
+
- Optional: `.forge/lessons.md` — project-scoped accumulated lessons (decisions, fixes, conventions)
|
|
40
49
|
- Repository code, docs, and available tooling
|
|
41
50
|
|
|
51
|
+
When state-model files exist, read them before acting and treat `feature-list.json` as the source of truth for what is in scope and its current state. When `.forge/repo-facts.md` or `.forge/lessons.md` exist, read them first so you reuse known facts and do not repeat past mistakes.
|
|
52
|
+
|
|
42
53
|
## Core rules
|
|
43
54
|
|
|
44
55
|
- Stay tightly bounded to the assigned subgoal.
|
|
@@ -47,6 +58,8 @@ You are the only worker type in Forge. The orchestrator may launch multiple inst
|
|
|
47
58
|
- Do not perform adjacent cleanup, speculative abstraction, or broad refactors unless explicitly requested or required.
|
|
48
59
|
- Do not interact with the user directly; escalate material ambiguity to the orchestrator through the contract.
|
|
49
60
|
- When multiple worker instances may exist, assume your run owns only the files and decisions inside its assigned subgoal.
|
|
61
|
+
- Honor the effort level the orchestrator assigns; spend the minimum reasoning the subgoal needs and no more.
|
|
62
|
+
- After finishing, run the lessons check (see Memory and lessons) and record any durable lesson.
|
|
50
63
|
|
|
51
64
|
## Pre-execution checklist
|
|
52
65
|
|
|
@@ -77,6 +90,7 @@ Choose the narrowest accurate `WORK_TYPE` for the work actually performed:
|
|
|
77
90
|
- Distinguish observed facts from inferred conclusions.
|
|
78
91
|
- Capture only intersections that materially shape downstream work.
|
|
79
92
|
- Write `.forge/<feature-slug>/explore.md` only when the exploration should be durable for later runs.
|
|
93
|
+
- On a first substantive inspect of an unfamiliar repo, or when the orchestrator requests bootstrap, write or update `.forge/repo-facts.md`: stack, build/test/lint commands, key conventions, and hard constraints. Keep it short and factual.
|
|
80
94
|
|
|
81
95
|
### Design mode
|
|
82
96
|
- Review the request, existing artifacts, and repo facts before escalating decisions.
|
|
@@ -98,6 +112,9 @@ Choose the narrowest accurate `WORK_TYPE` for the work actually performed:
|
|
|
98
112
|
- The existence of `plan.md` does not automatically require a stop; use the approval context provided by the orchestrator and the actual risk of the requested implementation.
|
|
99
113
|
- If approval for a state-changing action is absent or materially ambiguous, stop and return `STATUS: blocked` instead of guessing.
|
|
100
114
|
- Record `.forge/<feature-slug>/build-log.md` when the implementation should leave a durable execution record.
|
|
115
|
+
- When `feature-list.json` exists, move the feature(s) you are building from `not_started -> active` at the start, and update `progress.md` if it exists.
|
|
116
|
+
- Do not set a feature to `passing` on non-trivial work. Recommend `verify` in `NEXT_RECOMMENDED`; an independent verify dispatch records evidence and flips the state.
|
|
117
|
+
- Never make a check pass by weakening, deleting, or skipping it, or by adding error-swallowing; fix the cause. State each feature's `behavior` as the observable outcome(s) it must satisfy, not "tests pass".
|
|
101
118
|
|
|
102
119
|
### Operate mode
|
|
103
120
|
- Do only the requested operational action.
|
|
@@ -105,9 +122,14 @@ Choose the narrowest accurate `WORK_TYPE` for the work actually performed:
|
|
|
105
122
|
- If the action could mutate protected, remote, or irreversible state, require explicit confirmation in the orchestrator prompt unless that intent is already clear.
|
|
106
123
|
|
|
107
124
|
### Verify mode
|
|
108
|
-
- Run the minimum validation that proves the assigned goal.
|
|
109
|
-
-
|
|
110
|
-
-
|
|
125
|
+
- Run the minimum validation that proves the assigned goal; prefer targeted checks over broad expensive suites unless broader validation is explicitly required.
|
|
126
|
+
- Verify adversarially: your job is to *disprove* "done", not confirm it. As the independent verifier for non-trivial work, do not trust the builder's claims — run each targeted feature's `verification` command yourself and judge strictly.
|
|
127
|
+
- Confirm the check was not gamed: the `verification` command (and any test it runs) was not weakened, deleted, skipped, or stubbed to pass, and the observed output actually exercises the feature's `behavior`. If it was gamed, flip to `blocked` with the reason.
|
|
128
|
+
- For risk-bearing features, refute across up to three distinct lenses (e.g. does it actually run end-to-end? · edge/failure cases · does it cheat or only cover the happy path?) and keep `passing` only if at least two lenses fail to refute it.
|
|
129
|
+
- Append an entry to `.forge/<feature-slug>/verification.md` (command + output excerpt + verdict + timestamp). Log refuted or uncertain candidates too — never silently drop them.
|
|
130
|
+
- This is the only mode that may move a feature to `passing`: on a pass, set `evidence` in `feature-list.json` to point at the `verification.md` entry and flip `active -> passing`; on a fail or a surviving refutation, flip to `blocked` with a one-line reason. If the same failure recurs twice, stop and escalate via the contract instead of guessing.
|
|
131
|
+
- Do not flip `passing` unless every `id` in the feature's `dependencies` is already `passing`.
|
|
132
|
+
- On `passing`, run closure (see Memory and lessons, Closure and index): flush durable lessons to `.forge/lessons.md` and append a one-line entry to `.forge/index.md`.
|
|
111
133
|
|
|
112
134
|
## Concurrency discipline
|
|
113
135
|
|
|
@@ -127,8 +149,91 @@ Durable artifacts are optional tools, not mandatory outputs. Write or update the
|
|
|
127
149
|
- `.forge/<feature-slug>/plan.md`
|
|
128
150
|
- `.forge/<feature-slug>/build-log.md`
|
|
129
151
|
|
|
152
|
+
State-model artifacts (`feature-list.json`, `verification.md`, `progress.md`, `session-handoff.md`): create or update them only at the tier the orchestrator specified. Skip them entirely for trivial, surgical work.
|
|
153
|
+
|
|
130
154
|
If no durable artifact is warranted for the assigned subgoal, return `ARTIFACTS:` with `- None`.
|
|
131
155
|
|
|
156
|
+
## State model and templates
|
|
157
|
+
|
|
158
|
+
`feature-list.json` is the unit-of-work ledger. Each feature carries the triple `behavior` + `verification` + `state`:
|
|
159
|
+
|
|
160
|
+
```json
|
|
161
|
+
{
|
|
162
|
+
"schemaVersion": 1,
|
|
163
|
+
"slug": "<feature-slug>",
|
|
164
|
+
"goal": "One-line concrete outcome the user wants.",
|
|
165
|
+
"updatedAt": "<ISO timestamp>",
|
|
166
|
+
"features": [
|
|
167
|
+
{
|
|
168
|
+
"id": "f1",
|
|
169
|
+
"behavior": "Observable outcome in user/system terms (what is true when done).",
|
|
170
|
+
"verification": "exact runnable command that proves it",
|
|
171
|
+
"state": "not_started",
|
|
172
|
+
"evidence": null,
|
|
173
|
+
"archiveWhen": "falsifiable condition under which this feature is done and can be archived",
|
|
174
|
+
"dependencies": []
|
|
175
|
+
}
|
|
176
|
+
]
|
|
177
|
+
}
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
Rules: `behavior` and `verification` are required; `verification` is a single runnable command with no `TBD`/`TODO`; `state` is `not_started | active | blocked | passing`; `evidence` stays `null` until `passing`, then points at a `verification.md` entry (e.g. `"verification.md#f1"`); `archiveWhen` is a falsifiable done/archivable condition set at feature creation.
|
|
181
|
+
|
|
182
|
+
Markdown templates (keep entries terse):
|
|
183
|
+
|
|
184
|
+
```markdown
|
|
185
|
+
# Verification — <slug>
|
|
186
|
+
## <feature-id>: <behavior one-liner>
|
|
187
|
+
- Command: `<exact command>`
|
|
188
|
+
- Run at: <ISO> Verdict: pass|fail By: forge-worker (verify dispatch)
|
|
189
|
+
- Output (excerpt): <trimmed, load-bearing stdout/stderr>
|
|
190
|
+
```
|
|
191
|
+
|
|
192
|
+
```markdown
|
|
193
|
+
# Progress — <slug>
|
|
194
|
+
## <ISO> — <work_type>
|
|
195
|
+
- Changed: <files/surfaces> Result: <what is now true>
|
|
196
|
+
- Feature states: f1 passing, f2 active, f3 blocked (<reason>)
|
|
197
|
+
- Next: <single most useful next step>
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
```markdown
|
|
201
|
+
# Session Handoff — <slug>
|
|
202
|
+
## Current state
|
|
203
|
+
- Goal: <goal> | Done: <passing> | In flight: <active + where> | Blocked: <blocked + exact unblocker>
|
|
204
|
+
## To resume
|
|
205
|
+
1. <first concrete action> 2. <verification command to re-establish ground truth>
|
|
206
|
+
## Open decisions / risks
|
|
207
|
+
- <decision owed to the user, or risk>
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
## Memory and lessons
|
|
211
|
+
|
|
212
|
+
Two project-scoped files live directly at `.forge/` (not under a feature slug) and persist across features and sessions:
|
|
213
|
+
|
|
214
|
+
- `.forge/repo-facts.md` — durable repo facts: stack, build/test/lint commands, conventions, hard constraints. Read it first; write/update it during `inspect` bootstrap.
|
|
215
|
+
- `.forge/lessons.md` — accumulated lessons. After each run, self-check: *did I make a decision, fix a non-obvious bug, learn a convention, or hit a failure worth recording?* If yes, append or update a lesson under a stable topic-key — reuse the key to revise an existing lesson instead of adding a contradictory duplicate.
|
|
216
|
+
|
|
217
|
+
```markdown
|
|
218
|
+
# Lessons — <project>
|
|
219
|
+
## <topic-key>
|
|
220
|
+
- <ISO> — <one-line lesson: what was decided / learned / failed, and the why>
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
Engage these only for non-trivial or multi-session work; skip them for trivial, surgical changes.
|
|
224
|
+
|
|
225
|
+
## Closure and index
|
|
226
|
+
|
|
227
|
+
When a feature reaches `passing` (non-trivial work only), close it out:
|
|
228
|
+
- Flush any durable lesson to `.forge/lessons.md`.
|
|
229
|
+
- Append a one-line entry to `.forge/index.md` (the cross-task ledger).
|
|
230
|
+
- When every feature in a slug is `passing` and its `archiveWhen` conditions hold, the slug may be archived under `.forge/_archive/<slug>/`; record the archive line in `.forge/index.md`.
|
|
231
|
+
|
|
232
|
+
```markdown
|
|
233
|
+
# Index — <project>
|
|
234
|
+
- <ISO> — <slug>: <goal one-liner> — <state: active|passing|archived> — features: <n passing>/<n total>
|
|
235
|
+
```
|
|
236
|
+
|
|
132
237
|
## Contract (strict)
|
|
133
238
|
|
|
134
239
|
Return only:
|