Review and gates

After the build, Guild Stack reviews the work and writes review.md. Review is a role, not a favor: every run resolves who drafts, who advises, and who critiques — and a strong critique must come from a different host family than the author. The Power layer covers the roles and every review control. The Architect layer covers the release-path gates.

Try it. Ask for a cross-host review on one task. A different host family then critiques the work before the gate passes. If only one host is set up, Guild Stack warns you and a fresh same-host reviewer does it instead, marked weak:

/guild:guild add a --version flag to src/index.js --review=cross

Operating model and review roles

Every run resolves three roles. Each role names a host that does one job.

RoleJob
hostRuns the work: drafts and dispatches.
advisoryAnswers an advisor consult when a lane escalates a sub-question.
adversarialCritiques an artifact in cross-host review.
Three roles resolved at run start: host drafts, advisory answers consults, adversarial reviews at the gates, with the adversarial role needing a different host family from the author to count as strong.
Open full size

Default behavior

The roles are resolved once, at run-start preflight, from the capability matrix of the hosts detected on the machine. The resolver reads capability columns, not host names. The result is recorded in the run snapshot as guild.role_resolution.v1.

On a box with Claude and an authenticated Codex, the default is:

  • host = claude
  • advisory = claude (the local advisor)
  • adversarial = codex, strength strong

Each resolved role carries a strength of strong or weak, and a reason. An adversarial role is strong only when it is a different host family from the host. If the author host identity is not verified, a strong adversarial role is downgraded to weak.

Role pins

You cannot pin a role to a host in a durable file in v3.0.0. The settings schema still has roles.host, roles.advisory and roles.adversarial (default null), but /guild:config role refuses to write and config set refuses roles.* host values. A host name in a durable file would tie an initiative to whichever provider was running. The host for a run is detected at run start and recorded as guild.session_binding.v1. /guild:config models inspect shows that binding read-only.

Host ids in that binding and in the registry are the 16 HOST_IDS: claude-code-cli, codex-cli, pi-cli, antigravity-cli, agents-file, claude-code-app, claude-code-web, codex-app, claude-ai-connector, cursor, github-copilot, opencode, rovo-dev, kiro, qoder and trae. See Host matrix.

To influence review without naming a host, use the policy keys review.critic and review.independence (see Config reference), the --review flag below, and adversarial_review_provider.

--review

--review=local|cross|off is accepted on /guild:guild. The same key lives in settings as review. The default is local.

  • local (default) and off: you did not ask for cross-host review.
  • cross: the Claude and Codex adversarial review broker engages, and a different host family critiques the artifact.

Cross-host review is policy-gated. The broker fires when risk is high or above, when review: cross is set, or when project config requires it. Otherwise it resolves skipped and the gate passes with no reviewer. Self-build runs treat cross-host review as always on.

Gates

The broker has seven gates. Each fires inside the skill that produces the artifact.

GateArtifact reviewed
G-initInit artifact or wiki diff
G-specThe spec, before team composition
G-planThe plan, before the approval gate
G-laneOne lane's handoff receipt, before the next lane dispatches
G-qualityThe quality report
G-operationsThe ops record or runbook
G-diagnoseThe diagnosis or fix plan

Only G-lane is command-visible, because it fires per lane during build. The other six are skill-internal.

G-lane

After each lane's receipt is confirmed, the broker is called with gate G-lane:<task-id>. Lanes run in series. The trail for the lane is written to .guild/runs/<run-id>/review/G-lane:<task-id>/ as packet, result and trail.

On rework, the lane re-executes with the findings as added context. The re-run counts against the restart:<lane> counter. On satisfied, skipped or force_passed, the next lane proceeds.

Independence rule and degradation

The reviewer must be a different host family from the author. A same-family reviewer never counts as a cross-host sign-off.

When review is required but no different-family reviewer is available, the broker does not skip. It prints a warning, runs a fresh-context same-host review, and stamps it independence: weak. The weak review is still gated by the same 5-condition rule. Skipping is legal only when review was not required.

An adapter round that returns no verdict (refusal, dispatch error, empty response) never clears the gate and is not a skip. It offers the same three options as the round cap.

Provider pin: adversarial_review_provider

adversarial_review_provider defaults to auto. With auto, provider detection picks the best available different-family provider on every run and never persists the choice. You can pin codex-plugin or codex-cli. The pin is honored only when review is cross.

  • A native plugin adapter ranks above an authenticated CLI: codex-plugin before codex-cli.
  • pi and antigravity are detect-only. They are not selectable as reviewers.
  • Pinning a same-family provider, or a provider with no adapter, is refused with a reason. Guild Stack does not silently substitute.
  • Do not set the provider to a host id such as codex. The role names a host family. The provider is the concrete adapter.

Round cap: codex_cap and --codex-cap

Each gate loops until the reviewer reports satisfaction or the cap is hit. The cap resolves in this order: --codex-cap=N, then codex_cap in settings, then the default of 5. The maximum is 10. Values above 10 are clamped with a warning.

At round cap + 1 the broker stops and asks you to choose:

  • force-pass: proceed without cross-family sign-off. The trail stays for audit.
  • extend-cap N: continue for N more rounds, N from 1 to 5.
  • rework: return to the prior step and revise the artifact.

It waits for an explicit choice.

Skip enforcement: codex_skip_enforcement

A Stop hook (hooks/maybe-reflect.ts) tracks consecutive self-build reflections where cross review was skipped. It writes .guild/codex-skip-streak.json (guild.codex_skip_streak.v1). At the start of every gate the broker reads it. Only blocked: true matters. A missing or unreadable file means no block.

codex_skip_enforcementWhen blocked: true
warn (default)Print the warning and continue the gate.
blockRefuse the gate until the sentinel clears or you override. Classified as a security-sensitive key.

A reflection recording codex_review: RAN clears the sentinel.

Adversarial review and release gates

A change reaches stable only through gates. This section lists the gates verified for v3.0.0.

The gates

  1. Push. The .githooks/pre-push hook refuses direct pushes to main and next. Bypass: GUILD_ALLOW_PUSH_MAIN=1, for emergencies only.
  2. Channel integrity. Between a release and its dev bump, channel-integrity accepts a shared bare version only while main is tagged and the next tree equals it. Code PRs into next are blocked in that window.
  3. Branch policy. branch-policy.yml rejects any PR into main whose head is not the same-repository, exact next branch. All forks are rejected.
  4. Promotion. The gate refuses a beta manifest (manifest_version_not_release) and evidence not built at the exact bare version (source_version_not_release).
  5. Merge. The release PR must be a merge commit. CI requires the merged tree to equal the reviewed next tree and re-runs the promotion evidence.
  6. Conformance. The decision admits the full fixed set of 31 conformance scenarios, re-judged suite-wide. An extension outcome conforms only if it passed or was explicitly refused.

Refusal is tested, not assumed

The v3.0.0 evidence includes 18/18 planted refusal controls refusing.

Adversarial review

After each lane receipt, the review broker decides whether a G-lane review is required. If it is, the lane output and the reviewer verdict pass through the gate below. The gate passes only when every condition holds.

G-lane review gate funnel.
Open full size