flow-workflows 0.66.0 → 0.68.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/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
  # flow-workflows
2
2
 
3
3
  Guided `feat` / `bug` workflows for terminal coding agents: a ticket reaches an open MR/PR through explicit, reviewable phases, not one big prompt.
4
- For developers running Claude Code (or opencode, Gemini CLI, Codex CLI, Hermes Agent) on real repos with tickets, reviewers and a deploy.
4
+ For developers running Claude Code (or zcode, opencode, Gemini CLI, Codex CLI, Hermes Agent) on real repos with tickets, reviewers and a deploy.
5
5
  You get named phases, an artifact on disk after each one, hard gates the agent never crosses alone, and an autonomy dial from "ask me everything" to "run it and record what you decided".
6
6
 
7
7
  ## Quickstart
@@ -23,6 +23,14 @@ codex plugin add flow@flow-plugins
23
23
  # then, in a new session: $flow:init · $flow:next
24
24
  ```
25
25
 
26
+ **zcode** — same plugin, from its own marketplace
27
+
28
+ ```bash
29
+ zcode plugins marketplace add mashware/flow-workflows
30
+ zcode plugins install flow@flow-plugins
31
+ # then, in a new session: /flow:init · /flow:next
32
+ ```
33
+
26
34
  **opencode, Gemini CLI, Hermes Agent** — one command, nothing to clone
27
35
 
28
36
  ```bash
@@ -194,7 +202,7 @@ Artifacts are **hand-editable**: rewrite `03-design.md` and the next phase respe
194
202
  ## Configuration: base plus harness overlay
195
203
 
196
204
  `FLOW.md` at the repo root is the shared base. `FLOW.claude.md`, `FLOW.codex.md`,
197
- `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md` can sparsely override values for the product executing the
205
+ `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or `FLOW.zcode.md` can sparsely override values for the product executing the
198
206
  command. Existing repos with only `FLOW.md` behave exactly as before; anything effectively empty
199
207
  is auto-detected or asked for.
200
208
 
@@ -269,7 +277,12 @@ compaction point — selective, on disk and reversible.
269
277
  → [PHILOSOPHY](docs/PHILOSOPHY.md#nothing-here-asks-you-to-compact)
270
278
 
271
279
  Cost figures in these docs are estimates, not measurements: the flow reports how many agents a
272
- command launched, not how many tokens they spent.
280
+ command launched, not how many tokens they spent. **Quality used to be in the same position and no
281
+ longer is, for one command.** `/flow:feat:review` has a bench —
282
+ [`plugins/flow/evals/`](plugins/flow/evals/README.md) — that runs it over fixtures whose outcome is
283
+ known: a defect seeded at a known `file:line` the review has to raise, and a clean diff where any
284
+ blocker it reports is a false positive. Every other phase is still argued from judgement, and the
285
+ design decisions inside `review` itself were too, until there was something to check them against.
273
286
 
274
287
  ## Other harnesses
275
288
 
@@ -279,6 +292,7 @@ The same commands, in each harness's own shape. Only the invocation syntax diffe
279
292
  |---|---|---|
280
293
  | **Codex CLI** | `codex plugin add flow@flow-plugins` (see [Quickstart](#quickstart)) | `$flow:feat-start` |
281
294
  | **Codex CLI**, one repo only | `npx flow-workflows install codex project` → `.agents/skills/` | `$flow-feat-start` |
295
+ | **zcode** | `zcode plugins install flow@flow-plugins` (see [Quickstart](#quickstart)) | `/flow:feat:start` |
282
296
  | **opencode** | `npx flow-workflows install opencode` | `/flow-feat-start` |
283
297
  | **Gemini CLI** | `npx flow-workflows install gemini` | `/flow:feat:start` |
284
298
  | **Hermes Agent** | `npx flow-workflows install hermes` | `/flow-feat-start` |
@@ -288,6 +302,11 @@ dropped upstream does not linger. `npx flow-workflows check` compares what your
288
302
  against the newest release. From a clone, `adapters/install.sh <harness> [project]` does the same
289
303
  thing without Node; the preflight installs both ways and fails if the results differ by one byte.
290
304
 
305
+ **zcode** reads this plugin package directly and names a command after its path, with no plugin
306
+ prefix — so the `/flow:`-prefixed set it installs is a generated mirror living beside the Claude
307
+ one, and the plugin's own pages also show up there unprefixed (`/feat:start`, `/init`, …). Those
308
+ name Claude's overlay, so type the `/flow:` names.
309
+
291
310
  The mirrors are **generated** from the plugin commands by `script/adapter-build.py` and checked mechanically on every preflight (format, prefix, cited paths, install location).
292
311
  They have **not** been executed end to end in those harnesses — validate as you use them. → [adapters/README](adapters/README.md)
293
312
 
@@ -314,6 +333,7 @@ flow-workflows/
314
333
  ├── .github/ preflight CI · issue forms · PR template
315
334
  ├── plugins/flow/
316
335
  │ ├── commands/ feat/ bug/ work/ + next, init, doctor, news
336
+ │ ├── codex-skills/ · zcode-commands/ # generated mirrors for the two other plugin hosts
317
337
  │ ├── skills/flow-core/ # shared rules, loaded once per session
318
338
  │ ├── hooks/ push guard · update notice · where-you-left-off notice
319
339
  │ └── examples/ FLOW.template.md · symfony/ (a worked example, never loaded)
@@ -335,9 +355,10 @@ bash script/tests/push-guard.sh # the push guard's cases
335
355
  bash script/tests/notify-update.sh # the update-notice hook's cases
336
356
  bash script/tests/session-start.sh # the where-you-left-off hook's cases
337
357
  bash script/tests/review-unwrap.sh # the answer shapes `flow review` has to unwrap
358
+ bash script/tests/bench-compare.sh # the reader that compares two runs of the review bench
338
359
  ```
339
360
 
340
- CI runs the same six on every PR. The preflight refuses what has shipped broken before: an empty tracked file, unparsable JSON or TOML, a manifest version out of step with `CHANGELOG.md`, a hook without its executable bit, a stale or unusable mirror. → [RELEASING](RELEASING.md)
361
+ CI runs the same seven on every PR. The preflight refuses what has shipped broken before: an empty tracked file, unparsable JSON or TOML, a manifest version out of step with `CHANGELOG.md`, a hook without its executable bit, a stale or unusable mirror. → [RELEASING](RELEASING.md)
341
362
 
342
363
  ## What it does not ship (on purpose)
343
364
 
@@ -6,8 +6,9 @@ The `flow` plugin (in `../plugins/flow`) is for **Claude Code**. These adapters
6
6
  rules in `../plugins/flow/skills/flow-core/SKILL.md`, and writes every file under
7
7
  `opencode/commands/`, `codex/skills/`, `gemini/commands/flow/`, `hermes/skills/` plus one
8
8
  `<harness>/CORE.md` each —
9
- and `../plugins/flow/codex-skills/`, the same Codex skills packaged inside the plugin so
10
- `codex plugin add` installs them (see `codex/README.md`).
9
+ and the two mirrors that live inside the plugin package itself: `../plugins/flow/codex-skills/`,
10
+ the same Codex skills so `codex plugin add` installs them (see `codex/README.md`), and
11
+ `../plugins/flow/zcode-commands/`, the `/flow:`-prefixed set zcode reads (see the zcode row below).
11
12
  The **logic and prose are the plugin's, verbatim** — only the wrapper changes.
12
13
 
13
14
  | Harness | Commands | Subagents | MCP | Autopilot watch |
@@ -17,6 +18,7 @@ The **logic and prose are the plugin's, verbatim** — only the wrapper changes.
17
18
  | **Codex CLI** | `skills/*/SKILL.md` (`$flow-feat-start`) | `[agents.*]` in `config.toml` | `[mcp_servers.*]` | cron + `codex exec` |
18
19
  | **Codex CLI, packaged** | `plugins/flow/codex-skills/` (`$flow:feat-start`) | same | same | same |
19
20
  | **Hermes Agent** | `skills/*/SKILL.md` (`/flow-feat-start`) | `delegate_task`, built from the prompt | `config.yaml` `mcp_servers` | **native** `/cron add` |
21
+ | **zcode, packaged** | `plugins/flow/zcode-commands/flow/**` (`/flow:feat:start`) | `Agent` + `subagent_type`, as in Claude Code | `mcp.servers` in `~/.zcode/cli/config.json` | **native** `ScheduleWakeup` |
20
22
 
21
23
  ## What the generator changes per harness
22
24
 
@@ -30,7 +32,13 @@ Only the mechanics, and only these:
30
32
  Codex plugin package (Codex namespaces a plugin's skills), `/flow:feat:build` for Gemini. Hermes
31
33
  invokes its skills with a slash, so it shares opencode's `/flow-feat-build`: the file is shaped
32
34
  like Codex's, the prefix is opencode's.
33
- - **`$ARGUMENTS`** → `{{args}}` for Gemini.
35
+ - **`$ARGUMENTS`** → `{{args}}` for Gemini. zcode reads `$ARGUMENTS`, like Claude Code.
36
+ - **Nothing at all, for zcode** — it reads this plugin's own format and exposes the same
37
+ primitives under the same names, so its mirror is the Claude page with the overlay flag changed
38
+ to `--harness zcode` and one `flow/` folder above the command tree. That folder is the whole
39
+ trick: zcode names a command after its path under the root it was found in and adds no plugin
40
+ prefix, so `feat/start.md` on its own would be `/feat:start` — colliding with zcode's built-ins
41
+ (`/init`, `/doctor`) and with the user's own commands.
34
42
  - **The CORE pointer** — the plugin's `flow:flow-core` skill and `${CLAUDE_PLUGIN_ROOT}` become
35
43
  `~/.claude/flow/CORE.<tool>.md`, the file `install.sh` places there. In the Codex package they stay
36
44
  a skill (`$flow:flow-core`) and a relative root (`../..`), because there both actually exist.
@@ -17,7 +17,7 @@ Every `$flow-*` command assumes these rules. They are stated once, here, so a co
17
17
  carries what is specific to its phase. Read this once per session; a command that says "load
18
18
  `flow-core`" means this file.
19
19
 
20
- **This file belongs to flow `0.66.0`.** Compare it once, at the start of the session, against
20
+ **This file belongs to flow `0.68.0`.** Compare it once, at the start of the session, against
21
21
  `version` in `~/.claude/flow/.claude-plugin/plugin.json`. The two differing means the session
22
22
  is running a **mixture** — the commands from one copy of the plugin, these shared rules from another
23
23
  — which is exactly what happens when a branch or a release candidate is loaded over an installed
@@ -38,10 +38,14 @@ a command relies on is simply absent in that session, and nothing else will repo
38
38
  them. **Name the files this listing found the first time a phase reports any configured value**,
39
39
  so a missed overlay is visible in the artifact rather than invisible everywhere.
40
40
  - Read `FLOW.md` at the repo root as the base, then the optional overlay for the harness running
41
- this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or
42
- `FLOW.hermes.md`. The
41
+ this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`,
42
+ `FLOW.hermes.md`, or `FLOW.zcode.md`. The
43
43
  harness is the product executing the command, never guessed from a model name. An overlay is
44
- valid without a base file; unknown `FLOW.*.md` names are ignored. Throughout every command,
44
+ valid without a base file; unknown `FLOW.*.md` names are ignored. **A page can outlive the product it
45
+ was written for**: zcode reads the plugin's Claude pages as well as its own `/flow:`-prefixed
46
+ mirror of them, so a `claude` in a path or in a `--harness` flag records where the page was
47
+ written, never who is running it. On zcode the overlay is `FLOW.zcode.md` and the flag is
48
+ `--harness zcode`, whichever of the two pages you were handed. Throughout every command,
45
49
  **"FLOW.md" means this effective merged configuration** unless the command explicitly names a
46
50
  file it will edit.
47
51
  - **"The repo root" is the main checkout's, not the worktree's.** With `git.worktree` set, every
@@ -61,6 +65,15 @@ a command relies on is simply absent in that session, and nothing else will repo
61
65
  base branch — and goes out in no MR/PR at all. So a phase writing a tracked file writes it
62
66
  **here**, in the directory it is running in, and `$flow-feat-ship §5.5` is what catches the
63
67
  tools that could not be told.
68
+ - **A fenced block in a FLOW file is an example, and an example is not configuration.** These
69
+ files are prose with keys in them, and the rule that decides what a key *is* — a `- key:` line
70
+ under a `## section` — knows nothing about triple backticks. So a block written to be pasted
71
+ ("add this to try it once") was read as the configuration it illustrates, for as long as it sat
72
+ there. It happened in a real repo: `agents.exec_cmd` came from the fenced example of a file whose
73
+ prose argued at length that it was deliberately unset, and every review round took the one-shot
74
+ path that prose warned against — with nothing anywhere to say so, because the file and the
75
+ configuration disagreed while both looked right. **Skip fenced regions when you read a FLOW
76
+ file**; `flow-workflows` does the same, so the two of you resolve the same config.
64
77
  - Merge by section and key. A key present in the active overlay replaces the base value; a key
65
78
  absent there inherits the base. **A present-but-empty overlay key masks the base** and resolves
66
79
  to the normal empty-key fallback — this is how Codex can inherit its session model while a legacy
@@ -129,6 +129,10 @@ Whether the world they describe exists —
129
129
  CLIs installed *and authenticated*, agents discoverable, hooks executable, the MCP reachable, the
130
130
  base branch resolvable — is §2 below; flag the key here, check the world there, never both.
131
131
 
132
+ - **Keys inside a fenced block**: report them, one line, naming the file and the keys — they are
133
+ an example and resolve to nothing (flow-core §0), which is exactly what a reader who pasted a
134
+ block to enable it cannot tell from a key that works. Say what to do about it: move the line out
135
+ of the fence to make it real, leave it there to keep it an illustration.
132
136
  - **Fan-out and cost ceilings**: `agents.fanout_max` must be a positive integer; else flag and note
133
137
  the default `4` applies. `agents.budget_max` must be a non-negative integer (`0` = no ceiling);
134
138
  else flag and note the default `12`. **Both absent → say so as a finding, not a pass**: the review
@@ -20,9 +20,10 @@ description: "Assistant that generates FLOW.md and its optional harness overlay
20
20
 
21
21
  Creates or updates the effective FLOW configuration at the repo root: shared values in `FLOW.md`
22
22
  and optional harness-owned values in the active `FLOW.<harness>.md`. The active filename is
23
- `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md`;
24
- identify it from the
25
- product executing this command, never from the selected model. Every other `$flow-*` command reads
23
+ `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or
24
+ `FLOW.zcode.md`; identify it from the
25
+ product executing this command, never from the selected model (zcode runs the Claude pages too, so
26
+ the page you are reading does not name the harness). Every other `$flow-*` command reads
26
27
  the base and then that overlay. The user answers the **minimum**: what the repo can tell is
27
28
  auto-detected and only confirmed.
28
29
 
@@ -25,7 +25,7 @@ This system **orchestrates** the project's existing sub-agents and skills (it do
25
25
  - `FLOW.md` at the repo root is the shared base: tracker, branch and MR/PR conventions, quality
26
26
  commands, code conventions, and observability profile.
27
27
  - The active `FLOW.<harness>.md` is an optional sparse overlay (`claude`, `codex`, `opencode`,
28
- `gemini`, or `hermes`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
28
+ `gemini`, `hermes`, or `zcode`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
29
29
  differs on that harness. Every command reads the base and then the active overlay in step 0;
30
30
  existing repos with only `FLOW.md` behave exactly as before.
31
31
  - An overlay key replaces the base even when explicitly empty; an absent key inherits it. Lists
@@ -16,7 +16,7 @@ Every `/flow:*` command assumes these rules. They are stated once, here, so a co
16
16
  carries what is specific to its phase. Read this once per session; a command that says "load
17
17
  `flow-core`" means this file.
18
18
 
19
- **This file belongs to flow `0.66.0`.** Compare it once, at the start of the session, against
19
+ **This file belongs to flow `0.68.0`.** Compare it once, at the start of the session, against
20
20
  `version` in `~/.claude/flow/.claude-plugin/plugin.json`. The two differing means the session
21
21
  is running a **mixture** — the commands from one copy of the plugin, these shared rules from another
22
22
  — which is exactly what happens when a branch or a release candidate is loaded over an installed
@@ -37,10 +37,14 @@ a command relies on is simply absent in that session, and nothing else will repo
37
37
  them. **Name the files this listing found the first time a phase reports any configured value**,
38
38
  so a missed overlay is visible in the artifact rather than invisible everywhere.
39
39
  - Read `FLOW.md` at the repo root as the base, then the optional overlay for the harness running
40
- this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or
41
- `FLOW.hermes.md`. The
40
+ this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`,
41
+ `FLOW.hermes.md`, or `FLOW.zcode.md`. The
42
42
  harness is the product executing the command, never guessed from a model name. An overlay is
43
- valid without a base file; unknown `FLOW.*.md` names are ignored. Throughout every command,
43
+ valid without a base file; unknown `FLOW.*.md` names are ignored. **A page can outlive the product it
44
+ was written for**: zcode reads the plugin's Claude pages as well as its own `/flow:`-prefixed
45
+ mirror of them, so a `claude` in a path or in a `--harness` flag records where the page was
46
+ written, never who is running it. On zcode the overlay is `FLOW.zcode.md` and the flag is
47
+ `--harness zcode`, whichever of the two pages you were handed. Throughout every command,
44
48
  **"FLOW.md" means this effective merged configuration** unless the command explicitly names a
45
49
  file it will edit.
46
50
  - **"The repo root" is the main checkout's, not the worktree's.** With `git.worktree` set, every
@@ -60,6 +64,15 @@ a command relies on is simply absent in that session, and nothing else will repo
60
64
  base branch — and goes out in no MR/PR at all. So a phase writing a tracked file writes it
61
65
  **here**, in the directory it is running in, and `/flow:feat:ship §5.5` is what catches the
62
66
  tools that could not be told.
67
+ - **A fenced block in a FLOW file is an example, and an example is not configuration.** These
68
+ files are prose with keys in them, and the rule that decides what a key *is* — a `- key:` line
69
+ under a `## section` — knows nothing about triple backticks. So a block written to be pasted
70
+ ("add this to try it once") was read as the configuration it illustrates, for as long as it sat
71
+ there. It happened in a real repo: `agents.exec_cmd` came from the fenced example of a file whose
72
+ prose argued at length that it was deliberately unset, and every review round took the one-shot
73
+ path that prose warned against — with nothing anywhere to say so, because the file and the
74
+ configuration disagreed while both looked right. **Skip fenced regions when you read a FLOW
75
+ file**; `flow-workflows` does the same, so the two of you resolve the same config.
63
76
  - Merge by section and key. A key present in the active overlay replaces the base value; a key
64
77
  absent there inherits the base. **A present-but-empty overlay key masks the base** and resolves
65
78
  to the normal empty-key fallback — this is how Codex can inherit its session model while a legacy
@@ -125,6 +125,10 @@ Whether the world they describe exists —
125
125
  CLIs installed *and authenticated*, agents discoverable, hooks executable, the MCP reachable, the
126
126
  base branch resolvable — is §2 below; flag the key here, check the world there, never both.
127
127
 
128
+ - **Keys inside a fenced block**: report them, one line, naming the file and the keys — they are
129
+ an example and resolve to nothing (flow-core §0), which is exactly what a reader who pasted a
130
+ block to enable it cannot tell from a key that works. Say what to do about it: move the line out
131
+ of the fence to make it real, leave it there to keep it an illustration.
128
132
  - **Fan-out and cost ceilings**: `agents.fanout_max` must be a positive integer; else flag and note
129
133
  the default `4` applies. `agents.budget_max` must be a non-negative integer (`0` = no ceiling);
130
134
  else flag and note the default `12`. **Both absent → say so as a finding, not a pass**: the review
@@ -16,9 +16,10 @@ prompt = """
16
16
 
17
17
  Creates or updates the effective FLOW configuration at the repo root: shared values in `FLOW.md`
18
18
  and optional harness-owned values in the active `FLOW.<harness>.md`. The active filename is
19
- `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md`;
20
- identify it from the
21
- product executing this command, never from the selected model. Every other `/flow:*` command reads
19
+ `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or
20
+ `FLOW.zcode.md`; identify it from the
21
+ product executing this command, never from the selected model (zcode runs the Claude pages too, so
22
+ the page you are reading does not name the harness). Every other `/flow:*` command reads
22
23
  the base and then that overlay. The user answers the **minimum**: what the repo can tell is
23
24
  auto-detected and only confirmed.
24
25
 
@@ -21,7 +21,7 @@ This system **orchestrates** the project's existing sub-agents and skills (it do
21
21
  - `FLOW.md` at the repo root is the shared base: tracker, branch and MR/PR conventions, quality
22
22
  commands, code conventions, and observability profile.
23
23
  - The active `FLOW.<harness>.md` is an optional sparse overlay (`claude`, `codex`, `opencode`,
24
- `gemini`, or `hermes`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
24
+ `gemini`, `hermes`, or `zcode`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
25
25
  differs on that harness. Every command reads the base and then the active overlay in step 0;
26
26
  existing repos with only `FLOW.md` behave exactly as before.
27
27
  - An overlay key replaces the base even when explicitly empty; an absent key inherits it. Lists
@@ -17,7 +17,7 @@ Every `/flow-*` command assumes these rules. They are stated once, here, so a co
17
17
  carries what is specific to its phase. Read this once per session; a command that says "load
18
18
  `flow-core`" means this file.
19
19
 
20
- **This file belongs to flow `0.66.0`.** Compare it once, at the start of the session, against
20
+ **This file belongs to flow `0.68.0`.** Compare it once, at the start of the session, against
21
21
  `version` in `~/.claude/flow/.claude-plugin/plugin.json`. The two differing means the session
22
22
  is running a **mixture** — the commands from one copy of the plugin, these shared rules from another
23
23
  — which is exactly what happens when a branch or a release candidate is loaded over an installed
@@ -38,10 +38,14 @@ a command relies on is simply absent in that session, and nothing else will repo
38
38
  them. **Name the files this listing found the first time a phase reports any configured value**,
39
39
  so a missed overlay is visible in the artifact rather than invisible everywhere.
40
40
  - Read `FLOW.md` at the repo root as the base, then the optional overlay for the harness running
41
- this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or
42
- `FLOW.hermes.md`. The
41
+ this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`,
42
+ `FLOW.hermes.md`, or `FLOW.zcode.md`. The
43
43
  harness is the product executing the command, never guessed from a model name. An overlay is
44
- valid without a base file; unknown `FLOW.*.md` names are ignored. Throughout every command,
44
+ valid without a base file; unknown `FLOW.*.md` names are ignored. **A page can outlive the product it
45
+ was written for**: zcode reads the plugin's Claude pages as well as its own `/flow:`-prefixed
46
+ mirror of them, so a `claude` in a path or in a `--harness` flag records where the page was
47
+ written, never who is running it. On zcode the overlay is `FLOW.zcode.md` and the flag is
48
+ `--harness zcode`, whichever of the two pages you were handed. Throughout every command,
45
49
  **"FLOW.md" means this effective merged configuration** unless the command explicitly names a
46
50
  file it will edit.
47
51
  - **"The repo root" is the main checkout's, not the worktree's.** With `git.worktree` set, every
@@ -61,6 +65,15 @@ a command relies on is simply absent in that session, and nothing else will repo
61
65
  base branch — and goes out in no MR/PR at all. So a phase writing a tracked file writes it
62
66
  **here**, in the directory it is running in, and `/flow-feat-ship §5.5` is what catches the
63
67
  tools that could not be told.
68
+ - **A fenced block in a FLOW file is an example, and an example is not configuration.** These
69
+ files are prose with keys in them, and the rule that decides what a key *is* — a `- key:` line
70
+ under a `## section` — knows nothing about triple backticks. So a block written to be pasted
71
+ ("add this to try it once") was read as the configuration it illustrates, for as long as it sat
72
+ there. It happened in a real repo: `agents.exec_cmd` came from the fenced example of a file whose
73
+ prose argued at length that it was deliberately unset, and every review round took the one-shot
74
+ path that prose warned against — with nothing anywhere to say so, because the file and the
75
+ configuration disagreed while both looked right. **Skip fenced regions when you read a FLOW
76
+ file**; `flow-workflows` does the same, so the two of you resolve the same config.
64
77
  - Merge by section and key. A key present in the active overlay replaces the base value; a key
65
78
  absent there inherits the base. **A present-but-empty overlay key masks the base** and resolves
66
79
  to the normal empty-key fallback — this is how Codex can inherit its session model while a legacy
@@ -129,6 +129,10 @@ Whether the world they describe exists —
129
129
  CLIs installed *and authenticated*, agents discoverable, hooks executable, the MCP reachable, the
130
130
  base branch resolvable — is §2 below; flag the key here, check the world there, never both.
131
131
 
132
+ - **Keys inside a fenced block**: report them, one line, naming the file and the keys — they are
133
+ an example and resolve to nothing (flow-core §0), which is exactly what a reader who pasted a
134
+ block to enable it cannot tell from a key that works. Say what to do about it: move the line out
135
+ of the fence to make it real, leave it there to keep it an illustration.
132
136
  - **Fan-out and cost ceilings**: `agents.fanout_max` must be a positive integer; else flag and note
133
137
  the default `4` applies. `agents.budget_max` must be a non-negative integer (`0` = no ceiling);
134
138
  else flag and note the default `12`. **Both absent → say so as a finding, not a pass**: the review
@@ -20,9 +20,10 @@ description: "Assistant that generates FLOW.md and its optional harness overlay
20
20
 
21
21
  Creates or updates the effective FLOW configuration at the repo root: shared values in `FLOW.md`
22
22
  and optional harness-owned values in the active `FLOW.<harness>.md`. The active filename is
23
- `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md`;
24
- identify it from the
25
- product executing this command, never from the selected model. Every other `/flow-*` command reads
23
+ `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or
24
+ `FLOW.zcode.md`; identify it from the
25
+ product executing this command, never from the selected model (zcode runs the Claude pages too, so
26
+ the page you are reading does not name the harness). Every other `/flow-*` command reads
26
27
  the base and then that overlay. The user answers the **minimum**: what the repo can tell is
27
28
  auto-detected and only confirmed.
28
29
 
@@ -25,7 +25,7 @@ This system **orchestrates** the project's existing sub-agents and skills (it do
25
25
  - `FLOW.md` at the repo root is the shared base: tracker, branch and MR/PR conventions, quality
26
26
  commands, code conventions, and observability profile.
27
27
  - The active `FLOW.<harness>.md` is an optional sparse overlay (`claude`, `codex`, `opencode`,
28
- `gemini`, or `hermes`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
28
+ `gemini`, `hermes`, or `zcode`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
29
29
  differs on that harness. Every command reads the base and then the active overlay in step 0;
30
30
  existing repos with only `FLOW.md` behave exactly as before.
31
31
  - An overlay key replaces the base even when explicitly empty; an absent key inherits it. Lists
@@ -16,7 +16,7 @@ Every `/flow-*` command assumes these rules. They are stated once, here, so a co
16
16
  carries what is specific to its phase. Read this once per session; a command that says "load
17
17
  `flow-core`" means this file.
18
18
 
19
- **This file belongs to flow `0.66.0`.** Compare it once, at the start of the session, against
19
+ **This file belongs to flow `0.68.0`.** Compare it once, at the start of the session, against
20
20
  `version` in `~/.claude/flow/.claude-plugin/plugin.json`. The two differing means the session
21
21
  is running a **mixture** — the commands from one copy of the plugin, these shared rules from another
22
22
  — which is exactly what happens when a branch or a release candidate is loaded over an installed
@@ -37,10 +37,14 @@ a command relies on is simply absent in that session, and nothing else will repo
37
37
  them. **Name the files this listing found the first time a phase reports any configured value**,
38
38
  so a missed overlay is visible in the artifact rather than invisible everywhere.
39
39
  - Read `FLOW.md` at the repo root as the base, then the optional overlay for the harness running
40
- this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or
41
- `FLOW.hermes.md`. The
40
+ this command: `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`,
41
+ `FLOW.hermes.md`, or `FLOW.zcode.md`. The
42
42
  harness is the product executing the command, never guessed from a model name. An overlay is
43
- valid without a base file; unknown `FLOW.*.md` names are ignored. Throughout every command,
43
+ valid without a base file; unknown `FLOW.*.md` names are ignored. **A page can outlive the product it
44
+ was written for**: zcode reads the plugin's Claude pages as well as its own `/flow:`-prefixed
45
+ mirror of them, so a `claude` in a path or in a `--harness` flag records where the page was
46
+ written, never who is running it. On zcode the overlay is `FLOW.zcode.md` and the flag is
47
+ `--harness zcode`, whichever of the two pages you were handed. Throughout every command,
44
48
  **"FLOW.md" means this effective merged configuration** unless the command explicitly names a
45
49
  file it will edit.
46
50
  - **"The repo root" is the main checkout's, not the worktree's.** With `git.worktree` set, every
@@ -60,6 +64,15 @@ a command relies on is simply absent in that session, and nothing else will repo
60
64
  base branch — and goes out in no MR/PR at all. So a phase writing a tracked file writes it
61
65
  **here**, in the directory it is running in, and `/flow-feat-ship §5.5` is what catches the
62
66
  tools that could not be told.
67
+ - **A fenced block in a FLOW file is an example, and an example is not configuration.** These
68
+ files are prose with keys in them, and the rule that decides what a key *is* — a `- key:` line
69
+ under a `## section` — knows nothing about triple backticks. So a block written to be pasted
70
+ ("add this to try it once") was read as the configuration it illustrates, for as long as it sat
71
+ there. It happened in a real repo: `agents.exec_cmd` came from the fenced example of a file whose
72
+ prose argued at length that it was deliberately unset, and every review round took the one-shot
73
+ path that prose warned against — with nothing anywhere to say so, because the file and the
74
+ configuration disagreed while both looked right. **Skip fenced regions when you read a FLOW
75
+ file**; `flow-workflows` does the same, so the two of you resolve the same config.
63
76
  - Merge by section and key. A key present in the active overlay replaces the base value; a key
64
77
  absent there inherits the base. **A present-but-empty overlay key masks the base** and resolves
65
78
  to the normal empty-key fallback — this is how Codex can inherit its session model while a legacy
@@ -127,6 +127,10 @@ Whether the world they describe exists —
127
127
  CLIs installed *and authenticated*, agents discoverable, hooks executable, the MCP reachable, the
128
128
  base branch resolvable — is §2 below; flag the key here, check the world there, never both.
129
129
 
130
+ - **Keys inside a fenced block**: report them, one line, naming the file and the keys — they are
131
+ an example and resolve to nothing (flow-core §0), which is exactly what a reader who pasted a
132
+ block to enable it cannot tell from a key that works. Say what to do about it: move the line out
133
+ of the fence to make it real, leave it there to keep it an illustration.
130
134
  - **Fan-out and cost ceilings**: `agents.fanout_max` must be a positive integer; else flag and note
131
135
  the default `4` applies. `agents.budget_max` must be a non-negative integer (`0` = no ceiling);
132
136
  else flag and note the default `12`. **Both absent → say so as a finding, not a pass**: the review
@@ -18,9 +18,10 @@ description: Assistant that generates FLOW.md and its optional harness overlay (
18
18
 
19
19
  Creates or updates the effective FLOW configuration at the repo root: shared values in `FLOW.md`
20
20
  and optional harness-owned values in the active `FLOW.<harness>.md`. The active filename is
21
- `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md`;
22
- identify it from the
23
- product executing this command, never from the selected model. Every other `/flow-*` command reads
21
+ `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or
22
+ `FLOW.zcode.md`; identify it from the
23
+ product executing this command, never from the selected model (zcode runs the Claude pages too, so
24
+ the page you are reading does not name the harness). Every other `/flow-*` command reads
24
25
  the base and then that overlay. The user answers the **minimum**: what the repo can tell is
25
26
  auto-detected and only confirmed.
26
27
 
@@ -23,7 +23,7 @@ This system **orchestrates** the project's existing sub-agents and skills (it do
23
23
  - `FLOW.md` at the repo root is the shared base: tracker, branch and MR/PR conventions, quality
24
24
  commands, code conventions, and observability profile.
25
25
  - The active `FLOW.<harness>.md` is an optional sparse overlay (`claude`, `codex`, `opencode`,
26
- `gemini`, or `hermes`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
26
+ `gemini`, `hermes`, or `zcode`) for model names, agents, skills, orchestration, knowledge tools, or any other value that
27
27
  differs on that harness. Every command reads the base and then the active overlay in step 0;
28
28
  existing repos with only `FLOW.md` behave exactly as before.
29
29
  - An overlay key replaces the base even when explicitly empty; an absent key inherits it. Lists
package/bin/cli.mjs CHANGED
@@ -158,6 +158,17 @@ function claude() {
158
158
  console.log('Codex has its own too: codex plugin marketplace add https://github.com/mashware/flow-workflows.git')
159
159
  }
160
160
 
161
+ function zcode() {
162
+ console.log('zcode reads this plugin package directly, from its own marketplace, not from npm:')
163
+ console.log()
164
+ console.log(' zcode plugins marketplace add mashware/flow-workflows')
165
+ console.log(' zcode plugins install flow@flow-plugins')
166
+ console.log()
167
+ console.log('Then /flow:init in your repo. Updates arrive through `zcode plugins update flow`.')
168
+ console.log('Type the /flow:-prefixed commands: zcode also exposes the plugin\'s Claude pages')
169
+ console.log('unprefixed (/feat:start, /init, …), and those carry --harness claude.')
170
+ }
171
+
161
172
  function check() {
162
173
  const pkg = version()
163
174
  console.log(`this package: v${pkg}`)
@@ -229,7 +240,22 @@ function parseFlow(text) {
229
240
  const out = {}
230
241
  let section = null
231
242
  let listKey = null
243
+ let fence = null
232
244
  for (const line of text.split('\n')) {
245
+ // A fenced block is an illustration, not configuration. This reader knows headings and
246
+ // `- key:` lines and nothing else, so an example written the way `docs/CONFIGURATION.md`
247
+ // and every FLOW.md in the wild write one — keys inside triple backticks, under a sentence
248
+ // saying "paste this to try it" — was live config the whole time. A real repo had
249
+ // `agents.exec_cmd` set from the block of a file whose prose argued, at length, that it was
250
+ // deliberately unset, and every review round took the one-shot path it warned against.
251
+ // Closing fence: same character, at least as long as the opening one (CommonMark).
252
+ const f = /^\s{0,3}(`{3,}|~{3,})/.exec(line)
253
+ if (f) {
254
+ if (!fence) fence = f[1]
255
+ else if (f[1][0] === fence[0] && f[1].length >= fence.length) fence = null
256
+ continue
257
+ }
258
+ if (fence) continue
233
259
  const heading = /^##\s+(\S+)/.exec(line)
234
260
  if (heading) {
235
261
  section = heading[1]
@@ -276,7 +302,7 @@ const configRoot = (repo) => rootHolding(repo, 'FLOW.md')
276
302
  // The overlay names flow-core §0 recognises. A `--harness` outside this set reads no
277
303
  // overlay and looks exactly like a repo that has none, so it stops the run instead: a typo
278
304
  // here is worth one error message and never worth a review round nobody can trust.
279
- const OVERLAY_HARNESSES = ['claude', 'codex', 'gemini', 'hermes', 'opencode']
305
+ const OVERLAY_HARNESSES = ['claude', 'codex', 'gemini', 'hermes', 'opencode', 'zcode']
280
306
 
281
307
  // Every overlay sitting next to the base, whether or not this run reads one.
282
308
  function overlaysPresent(root) {
@@ -1107,8 +1133,9 @@ function usage() {
1107
1133
  Harnesses: ${Object.keys(HARNESSES).join(' · ')}
1108
1134
  "project" installs into the current repo instead of your user folder.
1109
1135
 
1110
- Claude Code and Codex CLI have their own marketplaces:
1136
+ Claude Code, Codex CLI and zcode have their own marketplaces:
1111
1137
  npx flow-workflows install claude shows how
1138
+ npx flow-workflows install zcode shows how
1112
1139
 
1113
1140
  "bundle" prints one context pack for the current branch — worklist, diff, the changed
1114
1141
  files in full, and the work's handoff — so a phase reads it in one call instead of
@@ -1161,10 +1188,11 @@ else if (cmd === 'cost') cost(process.argv.slice(3))
1161
1188
  else if (cmd === 'review') review(process.argv.slice(3)).catch((e) => { console.error(`flow review: ${e.message}`); process.exit(1) })
1162
1189
  else if (cmd === 'check') check()
1163
1190
  else if (cmd === 'install' && tool === 'claude') claude()
1191
+ else if (cmd === 'install' && tool === 'zcode') zcode()
1164
1192
  else if (cmd === 'install' && HARNESSES[tool]) install(tool, scope === 'project' ? 'project' : 'global')
1165
1193
  else if (cmd === 'install') {
1166
1194
  console.error(`Unknown harness: ${tool ?? '(none given)'}`)
1167
- console.error(`Expected one of: ${Object.keys(HARNESSES).join(', ')}, claude`)
1195
+ console.error(`Expected one of: ${Object.keys(HARNESSES).join(', ')}, claude, zcode`)
1168
1196
  process.exit(1)
1169
1197
  } else if (cmd === '--version' || cmd === '-v') console.log(version())
1170
1198
  else if (!cmd || cmd === '--help' || cmd === '-h' || cmd === 'help') usage()
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "flow-workflows",
3
- "version": "0.66.0",
3
+ "version": "0.68.0",
4
4
  "description": "Guided feat/bug workflows (start→ship), post-deploy monitoring and multi-agent code review, stack-agnostic. Each repo uses a shared FLOW.md plus optional harness overlay.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -23,6 +23,7 @@
23
23
  "gemini-cli",
24
24
  "codex",
25
25
  "hermes",
26
+ "zcode",
26
27
  "coding-agent",
27
28
  "feature-flow",
28
29
  "bug-flow"
@@ -3,7 +3,7 @@
3
3
  "name": "flow",
4
4
  "displayName": "Flow — guided dev workflows",
5
5
  "description": "Guided feat/bug workflows (start→ship), post-deploy monitoring and multi-agent code review, stack-agnostic. Each repo uses a shared FLOW.md plus optional harness overlay.",
6
- "version": "0.66.0",
6
+ "version": "0.68.0",
7
7
  "author": {
8
8
  "name": "Alberto Vioque",
9
9
  "email": "mashware@gmail.com"
@@ -17,5 +17,8 @@
17
17
  "git",
18
18
  "feature-flow",
19
19
  "bug-flow"
20
- ]
20
+ ],
21
+ "experimental": {
22
+ "evals": "evals"
23
+ }
21
24
  }
@@ -5,6 +5,117 @@ plugin and is what `/flow:news` reads to show you what changed since your previo
5
5
 
6
6
  The canonical, richest notes live in the [GitHub Releases](https://github.com/mashware/flow-workflows/releases).
7
7
 
8
+ ## v0.68.0 — The block written to be pasted was the configuration · 2026-09-21
9
+
10
+ **In short**
11
+ - **A fenced block in a FLOW file is an example again.** `- key:` lines inside triple backticks (or tildes) are skipped by `bin/cli.mjs` and by flow-core §0, so the two resolve the same configuration. Until now they were read as the config they illustrate.
12
+ - **This was found in a live repo, not imagined.** `agents.exec_cmd` was set from the fenced example of a file whose prose argued, at length, that it was deliberately unset — so every review round took the one-shot path that prose warned against, and nothing anywhere said so.
13
+ - **`/flow:doctor` reports keys found inside a fence**, names the file and says what to do: move the line out to make it real, leave it to keep it an illustration.
14
+ - **`script/tests/flow-config.sh`** pins it — fenced values never leak, `~~~` and four-backtick blocks are fences, a closed fence does not swallow the keys after it. Every case fails against the old reader.
15
+ - **Two tests now actually run in CI**: the new one and `tier.sh`, which existed and was wired into nothing.
16
+
17
+ A `FLOW.md` is prose with keys in it, and that is the point of it: the keys are the contract, the
18
+ prose is why the value is what it is. What decides which is which is shape alone — a `- key:` line
19
+ under a `## section` — and shape is exactly what a documented example shares with the thing it
20
+ documents. `docs/CONFIGURATION.md` teaches keys in fenced blocks. The template's own comments do.
21
+ So does every real `FLOW.md` that explains an option before enabling it.
22
+
23
+ The repo where this surfaced had a Claude overlay with three paragraphs on why `agents.exec_cmd`
24
+ stays unset — cost against the panel that had been finding the defects — followed by a block
25
+ introduced with *"to try it once, add both blocks below and take them out again afterwards"*. The
26
+ block was live from the moment it was written: `exec_cmd` set, `quality.reviewers` masked with four
27
+ role descriptions instead of the four agents the base names. The file and its configuration said
28
+ opposite things, and both looked right.
29
+
30
+ Nothing warns about that class of mistake, because the file is valid and the round it produces is
31
+ green. So the reader changes: fenced regions are skipped, by the CLI and by the command pages that
32
+ read the file themselves, and `doctor` reports what it found in one — a reader who pasted a block
33
+ to enable it needs to be told why it does nothing, which is the mirror of the same problem.
34
+
35
+ ## v0.67.0 — Every layer of the review was argued from judgement, and none was ever checked · 2026-09-21
36
+
37
+ **In short**
38
+ - **The review now has a bench.** `plugins/flow/evals/` runs `/flow:feat:review` over fixtures whose outcome is known before the review starts, and scores what came back: eight cases, five with a defect seeded at a known `file:line` the review has to raise, three with a clean diff where any blocker it reports is a false positive.
39
+ - **The seeded defects come from this repository's own history**, not from imagination — a value recorded after the mutation instead of before, a failing call reported as a clean result, a filter that drops the item it exists to carry, several writers on one shared key, a threshold that is code in one place and a literal in another. A defect we invent is a defect shaped like something we were already looking for.
40
+ - **Deterministic graders carry the score.** No judge model decides anything: a judge introduces the variance the bench exists to measure, and it changes the measuring stick exactly when the model changes. The `llm` grader is not used, and the two artifact checks that only the plugin can pass are marked as indicators outside the score, so the no-plugin arm stays comparable.
41
+ - **A difference inside the base's own range is not a difference.** `script/bench-compare.py` reads two runs, reports the **median** of each case rather than the mean the summary prints, and prints `—` for anything that lands inside the range the base's own runs spanned. A bench that reports every wobble as a regression is one everybody learns to ignore.
42
+ - **zcode is a harness the plugin knows.** It reads this same plugin package, so the commands were already there — but under names that collide with its built-ins, and resolving Claude Code's overlay. It now has its own `/flow:`-prefixed command set generated into the package, and `FLOW.zcode.md` is a recognised overlay everywhere, the CLI included.
43
+ - **Baselines are versioned and committed**, one per plugin version and model, under `evals/baselines/`. When a new model ships, the suite runs with `--model` and everything else frozen — which is the only way to find out that a layer which used to help has started costing turns.
44
+
45
+ Nothing in this repository could answer whether a change to `review` found more defects, fewer, or
46
+ the same ones more expensively. `script/check.py` proves the adapters match their sources byte for
47
+ byte and that a cited path exists; the hook tests pin behaviour that is deterministic by
48
+ construction. All of it checks **shape**, and the README already conceded half the gap — *"Cost
49
+ figures in these docs are estimates, not measurements"* — while saying nothing at all about the
50
+ other half.
51
+
52
+ That gap was not abstract. The completeness sweep, the data-access duel, the idiom audit, the
53
+ 150/600/1500 thresholds, the sensitive-surface bump: every one of them was argued from judgement,
54
+ and every one is now remembered as conviction. v0.66.0 wrote down the rule for retiring a pass —
55
+ no exclusive surviving finding across twenty reviews and it comes out of the command — and there
56
+ was no way to run twenty comparable reviews to trigger it. The same release made the tier
57
+ computable and nothing could say whether the tier it computed was the right one. Both shipped
58
+ instrumentation with no bench to read it on.
59
+
60
+ **A case is a repository, not a prompt.** Each one scaffolds a small tree, a flow work parked at
61
+ `build`, and a branch whose diff has a known outcome; the flow CLI is installed into the fixture
62
+ from this checkout, so the round takes the CLI path and not its documented fallback. The prompt
63
+ opens with the literal `/flow:feat:review` and then states the task in plain words — both halves
64
+ are load-bearing. Inside an eval run the agent cannot invoke a plugin command on its own: asked in
65
+ prose to use the review command it reads files instead and never reaches it, so only a prompt that
66
+ *is* the command gets there. The plain-words half is what the no-plugin arm answers, which is what
67
+ makes `Δ` mean anything.
68
+
69
+ **Both kinds of case are mandatory**, and the second kind is the one that is easy to skip. Without
70
+ a clean diff in the suite the score rewards the noisiest review there is, and noise is what makes
71
+ people stop reading reviews at all. One of the three sits on a path `quality.sensitive_paths` names
72
+ and moves a log level and nothing else — which is the judgement §2.0 says a CLI cannot make, checked
73
+ for the first time.
74
+
75
+ The release preflight gains the checks that keep the bench runnable — every case has its scaffold,
76
+ its prompt and its graders, the prompt still opens with the command under test, and the suite still
77
+ holds both kinds. Running it is deliberately **not** wired into `publish.yml`: that workflow puts
78
+ the package on npm in minutes, and ten cases at three runs across two arms is sixty full agent
79
+ sessions. `.github/workflows/bench.yml` runs at the release and on demand, and says so plainly when
80
+ the repository has no credential for it rather than standing red.
81
+
82
+ **What the first run said**, recorded here because a bench whose first result is left out of the
83
+ notes is a bench nobody will believe later. 8 cases × 3 runs × 2 arms, 48 sessions, 52 minutes,
84
+ $47.27, threshold 0.5, the CLI's default model: every case at or above the threshold, suite score
85
+ 0.96, and **mean Δ against the no-plugin arm of −0.04**. Seven of the eight cases scored 1.00 in
86
+ both arms; the eighth (`seeded-divergent-threshold`) scored 0.67 with the plugin and 1.00 without,
87
+ one run in three having missed it. The with-arm cost $1.57 and 4.5 minutes per run against $0.40
88
+ and 1.9 minutes — **3.9× for the same findings**.
89
+
90
+ The honest reading is about the fixtures before it is about the command, and the reason is
91
+ mechanical: every case is tagged `xs`, and **at XS the command runs the built-in `code-review`
92
+ alone** — no panel, and §3.5's sweep is M/L only. The layers this bench exists to judge did not run
93
+ once in those 48 sessions, so the two arms were doing nearly the same work. Eight single-file diffs
94
+ with a docstring stating the contract the code breaks is also a defect an unguided review finds,
95
+ which puts both arms on the ceiling, where a delta can only fall.
96
+
97
+ The second tier is written down rather than written: `deep` cases, M-sized, with a populated
98
+ reviewer roster, a defect split across files and its contract in `03-design.md`. They cost roughly
99
+ what they exercise, so the suite splits by tag and each tier keeps its own baseline.
100
+
101
+ Nothing is retired and no threshold moves here. The first run establishes the base; it does not
102
+ judge anything.
103
+
104
+ **zcode**, separately. It reads Claude-format plugin packages — `.zcode-plugin/plugin.json` first,
105
+ then `.claude-plugin/plugin.json` — and exposes the same primitives under the same names, so
106
+ installing flow from the marketplace worked on the first try and hid two things. A command is named
107
+ after its path with no plugin prefix, so the set arrived as `/feat:start`, `/next`, `/init` and
108
+ `/doctor` — the last two losing to zcode's own built-ins. And every `flow-workflows` call in the
109
+ pages carries `--harness claude`, which on zcode reads another product's overlay and reports, in the
110
+ pack's own header, that an overlay was read.
111
+
112
+ Both are fixed by generation, not by prose: `plugins/flow/zcode-commands/flow/**` is the same
113
+ generator's fifth target, the `flow/` folder is what makes zcode name them `/flow:feat:start`, and
114
+ the flag is substituted like it is for every other mirror. `FLOW.zcode.md` joins the overlay names
115
+ in flow-core, `init`, the template and the CLI — where an unknown `--harness` has always stopped
116
+ the run rather than silently reading the base. The plugin's own Claude pages still show up
117
+ unprefixed in zcode, so both the mirror's legend and the docs say to type the `/flow:` names.
118
+
8
119
  ## v0.66.0 — Every phase read a tree, and none of them could say which one · 2026-09-21
9
120
 
10
121
  **In short**
@@ -5,8 +5,8 @@ file in their step 0. Delete what does not apply; **empty or absent = auto-disco
5
5
  default behavior** (each command states what it does when a value is missing).
6
6
 
7
7
  Use this shape for the shared base `FLOW.md` and for an optional sparse harness overlay:
8
- `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, or `FLOW.hermes.md`. The
9
- active overlay is
8
+ `FLOW.claude.md`, `FLOW.codex.md`, `FLOW.opencode.md`, `FLOW.gemini.md`, `FLOW.hermes.md`, or
9
+ `FLOW.zcode.md`. The active overlay is
10
10
  read after the base. A key present in it replaces the base value; a present-but-empty key masks the
11
11
  base and selects the normal empty fallback; an absent key inherits the base. Lists replace whole
12
12
  lists. `conventions` is additive: overlay lines follow the base lines and both apply. Existing repos