Workflow file reference
A workflow is a directory containing one flow.* file and any prompt files referenced by its steps. It is the durable program for a multi-agent run: it names the steps, which agents run each step, how results feed forward, and what nax must wait for before continuing.
Council-style workflows usually start with independent new-run submissions, feed all first-pass results into a cross-review step, then send those outputs into one final synthesis step.
- flow.yml
Supported files
flow.yml, flow.yaml, flow.json, and flow.toml are supported.
JavaScript and TypeScript flows are supported when the entire module is a JSON5-compatible static object export. NAX parses the object as data and never executes project code; imports, declarations, function calls, and exported functions are rejected.
Top-level keys
| Key | Required | Purpose |
|---|---|---|
id | yes | Stable workflow id used by nax run <id>. |
title | yes | Human name shown in lists, prompts, and dashboard. |
description | recommended | One-sentence summary. |
disabled | no | Set to true to hide a workflow from nax list, nax run, and the dashboard without deleting its files. |
defaults | no | Default transport, notification, agents, models, and efforts. |
steps | yes | Ordered workflow steps. |
Step keys
| Key | Values | Purpose |
|---|---|---|
action | issue, comment, human-review | Submission or gate behavior. |
submit | new-run, follow-up | Start fresh or reuse prior context. |
agents | strings or instance objects | Ordered lineup. Strings are bare Auto providers; objects can pin or fan out model/models and effort/efforts. |
models | provider-keyed string map | Legacy bridge for pinning one unambiguous provider instance. Prefer instance objects. |
efforts | provider-keyed string map | Legacy bridge for one unambiguous pinned model. Prefer instance objects. |
input | [{ step, results }] | Earlier results to include. Use all for every result or peers to exclude each continuing instance’s own result. |
waitFor | agent-results | Wait until every configured agent has a result. |
Example
id: review
title: Review
description: Review, cross-review, and synthesize findings.
defaults:
transport: auto
agents: [claude, gemini, codex]
steps:
- id: review
title: Review
prompt: prompts/1_review.md
action: issue
submit: new-run
agents:
- { agent: claude, models: [claude-opus-5, claude-opus-4-8] }
- { agent: gemini, model: latest, effort: high }
- codex
waitFor: agent-results
- id: cross-review
title: Cross Review
prompt: prompts/2_cross-review.md
action: comment
submit: follow-up
input:
- step: review
results: peers
waitFor: agent-results
- id: synthesize
title: Summarize Consensus
prompt: prompts/3_synthesize.md
action: issue
submit: new-run
agents: [codex]
input:
- step: review
results: all
- step: cross-review
results: all
waitFor: agent-resultsEach normalized lineup entry becomes one agent instance. An instance has a
tuple-derived id: agent:model:effort, using auto for omitted fields. A bare
provider such as claude therefore becomes claude:auto:auto and sends no
model or effort. It does not silently resolve to the catalog flagship.
A step can contain at most four resolved instances. A follow-up step inherits
the surviving instances from its first input step. With results: peers, each
continued instance receives every surviving peer’s output while its own prior
work remains available through the continued runner session.
Instance objects accept model or models, plus effort or efforts.
Plural fields expand to their cartesian product:
agents:
# Model bake-off: two Claude instances.
- { agent: claude, models: [claude-opus-5, claude-opus-4-8] }
# Effort sweep: three more Claude instances.
- { agent: claude, model: claude-fable-5, efforts: [low, medium, high] }
# Alias resolved and recorded as a concrete model at launch.
- { agent: gemini, model: latest, effort: high, label: Gemini flagship }
# Bare provider: Auto on the wire.
- codexlatest and default resolve to the provider’s defaultModel at launch. A
retry or resume reuses the recorded concrete model; a fresh workflow run
resolves the alias again. Labels are display-only and cannot make duplicate
tuples distinct. Exact duplicates fail before remote work is created.
Legacy models and efforts maps remain valid when a provider occurs exactly
once as a bare string. They are rejected as ambiguous when the same provider
has multiple instances. The literal auto clears a legacy pin and is omitted
from the Agent Runner request.
Known provider/model or model/effort mismatches fail before submission.
Unknown future model and effort strings pass through with a warning so a
slightly stale NAX catalog does not block new backend capabilities. Do not use
an agentConfig wrapper.
Follow-up inheritance
A follow-up step does not declare an agents lineup. It inherits surviving
instances from the first step in input and continues each instance’s own
runner session by (sourceStepId, instanceId). Additional inputs supply
read-only context. Declaring agents on a follow-up is deprecated and ignored.
If some instances exhaust their retries, survivors continue and the step is
stored as completed_with_failures. If every instance fails, the workflow
halts before later steps. Local Netlify API execution keeps at most four
non-terminal runners active at once.
Current model and effort catalog
| Provider | Model IDs | Configurable effort |
|---|---|---|
| Claude | claude-opus-5, claude-opus-4-8, claude-fable-5, claude-sonnet-5, claude-haiku-4-5 | Low, Medium, High |
| Codex | gpt-5.6-sol, gpt-5.6-terra, gpt-5.6-luna, gpt-5.4-mini | Low, Medium, High |
| Gemini | gemini-3.1-pro-preview, gemini-3.6-flash, gemini-3.5-flash-lite | Low, Medium, High |
| OpenCode | moonshotai/kimi-k3 | Low, High, Max |
| OpenCode | moonshotai/kimi-k2.7-code | Auto only |
| OpenCode | z-ai/glm-5.2, deepseek/deepseek-v4-pro | High, Max (xhigh on the wire) |
| OpenCode | ~deepseek/deepseek-v4-flash-latest | Low, High, Max |
| OpenCode | x-ai/grok-4.5 | Low, Medium, High |
| OpenCode | minimax/minimax-m3 | Auto only |
The leading tilde in ~deepseek/deepseek-v4-flash-latest is part of the model
ID. The dashboard displays Max even where Agent Runner expects xhigh.
NAX 2.0 breaking change
NAX 2.0 does not accept the old provider-list meaning of models. Replace a
request such as --models claude,codex with --agents claude,codex, then add
real model assignments separately if needed. There is no compatibility alias.
NAX 2.1 artifact migration
Run state, status, retry selection, and artifacts are keyed by instance id
rather than provider. A step with one instance of a provider keeps the familiar
provider artifact basename. Multiple instances of the same provider use an
instance-scoped basename such as claude__claude-opus-5__high.md. Consumers
must not assume there is only one result per provider.
Project-local flows with the same id as bundled flows shadow the bundled version. This is useful when intentional and confusing when accidental.
See also
- Write custom workflows for a guided setup.
- Configuration reference for flow discovery.
- Security policies for safe-mode behavior.
- Council pattern for why independent passes feed cross-review and synthesis.
- Architecture for execution flow.