Workflows & Phases
A workflow is the workflow section of team.yml. It declares which phases exist, how they connect, and what configuration each phase carries. The orchestrator reads this definition, resolves the dependency graph, and executes phases in the right order.
A phase is one step in a pipeline. Every phase has a name and a type. The type determines what the orchestrator does — whether it launches an agent, runs automated commands, fetches external files, or all three.
For the complete field-by-field schema, see team.yml Reference.
workflow: phases: - name: architect type: standard
- name: developer type: standard depends_on: [architect]
- name: reviewer type: gate depends_on: [developer] commands: - name: tests run: npm test max_iterations: 3Phase Types
Section titled “Phase Types”| Type | Agent? | Commands? | What it does |
|---|---|---|---|
standard | Yes | Optional | Runs an agent that does work and signals done. With agent: exec, runs commands with no LLM. |
gate | Yes | Optional | Runs commands, then an agent renders a verdict (automated). With agent: hug, a human reviewer renders the verdict via the HUG review page. |
team | Built-in | No | Runs an entire sub-team pipeline; role becomes the requirements spec |
Data collection and delivery (fetching from Google Drive, Jira, S3, or pushing results to external systems) is handled by connector agents — standard phases that use a built-in connector agent like jira, gdrive, s3, curl, confluence, zendesk, datadog, or hubspot. See team.yml Reference — Sources and Target Entries for configuration.
Standard
Section titled “Standard”The workhorse. A standard phase launches an agent, gives it a role and the task requirements, and waits for it to signal completion. This is where the real work happens — writing code, designing architecture, authoring tests, producing documents.
- name: developer type: standard depends_on: [architect]The agent SDK reads the role file and incoming channel handoffs from predecessors, passes them to the implementation, captures the result, writes handoff notes for successors, and signals done.
Phase output: the handoff envelope
Section titled “Phase output: the handoff envelope”Every standard phase produces a handoff envelope — a JSON file with two parts that downstream phases can consume:
text— a natural language summary, automatically injected into downstream LLM agent promptsdata— a structured payload accessible via$(handoff.<phase>.<path>)template variables and in custom SDK agents
For LLM agents, text is the agent’s response and data carries any structured information. For connector agents (S3, Jira, Google Drive, curl, etc.), data contains enriched results with URLs, metadata, and local file paths in name-keyed maps. See the Agent Reference for the exact handoff structure each agent produces.
This dual structure means downstream phases get both human-readable context for LLMs and machine-readable data for template variables and programmatic access — from every phase, regardless of agent type.
A gate is a quality checkpoint that combines automated commands with agent intelligence. Gates create feedback loops that let work improve iteratively.
- name: reviewer type: gate depends_on: [developer] commands: - name: build run: npm run build - name: tests run: npm test max_iterations: 3How a gate runs
Section titled “How a gate runs”When a gate’s dependencies complete:
- Run commands — the orchestrator executes each command as a shell command (exit 0 = pass, non-zero = fail). Command outcomes are evaluated by the agent, not the orchestrator.
- Build gate context — command results and verdict history are written to
.cliq/gate_context.md - Launch the gate agent — the agent reviews the work and produces a structured verdict
Verdicts
Section titled “Verdicts”| Verdict | What happens |
|---|---|
| PASS | Quality bar is met. Pipeline continues to the next phase. |
| ROUTE:<phase> | Work needs revision. The named phase is re-activated with feedback. When it finishes, the gate re-evaluates from step 1. |
| ESCALATE | Human intervention required. The pipeline halts. |
The gate loop
Section titled “The gate loop”On a ROUTE verdict, the orchestrator:
- The gate writes its verdict envelope to the channel (e.g.
.cliq/channels/reviewer--developer/handoff.json) - Re-activates the target phase (which reads the feedback and fixes the issues)
- Waits for the target to signal done
- Re-runs the gate’s commands
- Launches the gate agent again with updated results and the growing verdict history
This loop continues until the gate passes, escalates, or exhausts its max_iterations budget. The default is 3 iterations; the maximum is 5. After the budget is spent, the orchestrator auto-escalates.
The gate agent sees the full history of previous verdicts, so it can make increasingly informed decisions — for example, escalating after a second failed route to the same phase.
Exec (agent)
Section titled “Exec (agent)”An exec configuration runs shell commands with no LLM agent and no prompt. Use type: standard with agent: exec. Each exec phase gets its own tmux pane where commands execute with real-time output. Each command has an optional escalate_on_fail boolean (default true). Commands with escalate_on_fail: false log failures as warnings and continue.
- name: git-verify type: standard agent: exec depends_on: [git-finalize] commands: - name: pushed run: "git ls-remote --heads origin $(git branch --show-current) | grep -q ." - name: changelog-updated run: "test -f CHANGELOG.md" escalate_on_fail: falseUse exec phases to verify that critical external actions actually happened — things like “was the code pushed?” or “was the changelog updated?” — where an agent’s self-report isn’t reliable enough. Exec phases must have at least one command and cannot have max_iterations.
HUG (Human Review Gate)
Section titled “HUG (Human Review Gate)”A HUG configuration pauses the pipeline for human review. Use type: gate with agent: hug and a nested review: block. Instead of an AI agent rendering the verdict, a real person reviews the work on a web-based review page and decides the outcome.
- name: human-review type: gate agent: hug depends_on: [developer] commands: - name: tests run: npm test review: reviewer: architects timeout: 48hHUG gates use the same PASS / ROUTE / ESCALATE verdict model as automated gates. The review.reviewer field is required — it tells the orchestrator who reviews. Optional artifacts, timeout, and remind_every fields within the review: block control which files to present and how long to wait.
See Human Gate (HUG) for the full setup and configuration.
A team phase delegates an entire step of your pipeline to another cliq team. Instead of launching a single agent, the orchestrator runs a full nested pipeline with its own workflow, roles, channels, and signals — all inside an isolated call frame under .cliq/team-phases/<phase_name>/.
- name: security-audit type: team depends_on: [developer] team: "@acme/security-scan" inputs: scan_target: src/
- name: fixer type: standard depends_on: [security-audit]Role files
Section titled “Role files”Like every other phase type, team phases require a role file in roles/. The role is the author’s instructions for what the sub-team should accomplish — it becomes the requirements spec passed to cliq req inside the call frame.
Analyze the project at $(dirs.project) for security vulnerabilities.
Focus on authentication, input validation, and dependency risks.Write your findings report to $(dirs.project)/reports/security-report.md.Team phase roles support special template variables for directory paths. See Roles — Team Phase Roles for the full list.
How a team phase runs
Section titled “How a team phase runs”At assembly time (cliq assemble):
- Recursive assembly —
cliq assemblerecursively resolves all sub-team references, assembling each into its call frame at.cliq/team-phases/<phase_name>/ - Hub download —
hub://references are downloaded from the remote registry and assembled locally - Input validation — declared inputs at every nesting level are validated against provided inputs
- Lockfile —
.cliq/team-lock.ymlis written at the project root, recording all hub-resolved teams with versions and integrity hashes
At runtime (when the team phase’s dependencies complete):
- Build spec — the built-in team agent combines the expanded role file (with
$(dirs.*)and$(inputs.*)resolved) and upstream channel content into a spec file - Run
cliq req— passes the spec and input values to the sub-team’scliq reqin the call frame - Run the sub-pipeline —
cliq run --headlesslaunches the sub-team’s full workflow - Write handoff — the team agent collects the sub-team’s task board and channel outputs into a structured handoff, sent to downstream phases via normal channels
The team agent is entirely deterministic — no LLM is involved. The human-authored role file is the spec; the handoff is a faithful pass-through of the sub-team’s own outputs.
Workspace isolation
Section titled “Workspace isolation”Every agent’s working directory (cwd) defaults to $(dirs.self) — the orchestration state directory for the current pipeline level. At top level, dirs.self equals the project root so nothing changes for single-team projects. In sub-teams, dirs.self is the call frame (.cliq/team-phases/<phase_name>/), which means bare relative paths resolve inside the call frame, not the project root.
| Concept | Top-level run | Sub-team run |
|---|---|---|
cwd (dirs.self) | Project root | Call frame path |
dirs.project | Project root | Project root (same) |
To read or write project files from a sub-team, use $(dirs.project) explicitly:
Write your report to $(dirs.project)/reports/security-report.md.This isolation prevents parallel team phases from stepping on each other via bare relative paths. cliq team validate and cliq assemble warn about bare relative paths that should be qualified with a $(dirs.*) prefix ($(dirs.project), $(dirs.self), or $(dirs.<phase>)) for portability. cliq team publish blocks them; pass --force only when the flag is a confirmed false positive.
Downstream access
Section titled “Downstream access”Downstream phases that depend on a team phase receive handoff content through normal channels — exactly like any other phase. The handoff includes the sub-team’s final task board and channel outputs. No special call-frame knowledge is needed.
Monitoring
Section titled “Monitoring”Each orchestrator — top-level and nested — runs a WebSocket event server. The team agent connects to the sub-orchestrator’s WebSocket and relays events up the call stack with prefixed phase names (e.g., security-audit.analyzer), giving full hierarchical visibility into nested pipelines.
Team references
Section titled “Team references”The team field accepts two reference styles:
| Style | Example | Resolved at |
|---|---|---|
| Local (installed) | "@acme/scanner" | Assembly time — from global install dir |
| Hub | "hub://@acme/scanner" or "hub://@acme/[email protected]" | Assembly time — downloaded from CliqHub |
References are explicit: there is no fallback search path. A local ref always resolves from the installed team registry. A hub ref always downloads from the remote registry.
Nesting
Section titled “Nesting”Team phases can nest recursively. A sub-team’s workflow can itself contain team phases, creating a call stack. Each level gets its own isolated call frame, but all levels share the same project workspace. cliq assemble detects cycles at assembly time and enforces a maximum of 50 teams per project to prevent runaway transitive dependencies.
Lockfile (.cliq/team-lock.yml)
Section titled “Lockfile (.cliq/team-lock.yml)”After recursive assembly, cliq writes a lockfile at the project root recording every hub-resolved team:
locked_at: "2026-04-30T18:00:00Z"teams: "@acme/scanner": version: "1.2.0" source: hub integrity: "sha256:abc123..."This provides a reproducibility audit trail. Future use: --offline mode could skip network calls using the lockfile.
Restrictions
Section titled “Restrictions”- Team phases require a role file — the role becomes the sub-team’s requirements spec
- Phase names cannot contain
.characters (dots are reserved for event name mangling in nested monitoring) - The
teamfield is required on team phases and not allowed on other types inputson a team phase are static key-value pairs passed to the sub-team atcliq reqtimecliq assemblemust be re-run whenever team references change
Dependencies and Parallelism
Section titled “Dependencies and Parallelism”Phases connect through depends_on. A phase won’t start until all of its dependencies have completed. Phases with no shared dependencies run in parallel automatically.
- name: architect type: standard
- name: tester type: standard depends_on: [architect]
- name: security-auditor type: standard depends_on: [architect]
- name: developer type: standard depends_on: [tester, security-auditor]Here, tester and security-auditor both depend on architect and nothing else — so they run simultaneously once the architect finishes. developer waits for both (fan-in). The orchestrator handles all of this from the depends_on declarations.
A phase with no depends_on is a root phase — it starts immediately when the pipeline runs. Every workflow must have at least one root phase.
Commands
Section titled “Commands”Commands are shell commands attached to gate and standard phases. Each command runs as a subprocess — exit code 0 means pass, non-zero means fail.
commands: - name: build run: npm run build scope: repo if: "test -f package.json" - name: tests run: npm test - name: output-exists run: "test -f output.md"See team.yml Reference — Commands for the full field reference.
Conditional commands
Section titled “Conditional commands”The if field lets you skip commands when they don’t apply:
- name: build run: npm run build if: "test -f package.json"If package.json doesn’t exist, the command is skipped — not failed. This is common in teams that work across different project types.
Multi-repo command scoping
Section titled “Multi-repo command scoping”By default, commands run from the current working directory ($(dirs.self)). In multi-repo setups, scope: repo runs the command in each repository:
- name: tests run: npm test scope: repo if: "test -f package.json"In a single-repo workspace, scope: repo behaves identically to scope: workspace.
Support Phases
Section titled “Support Phases”A support phase sits idle until a gate routes work to it. Support phases are declared in a separate support section under workflow, not in the main phases list.
workflow: phases: - name: developer type: standard - name: reviewer type: gate depends_on: [developer] commands: - name: tests run: npm test max_iterations: 3 support: - name: fixer type: standard - name: git-resolver type: standardSupport phases have their real functional type (standard, gate, etc.) — they’re just topologically separated from the main flow. They must not have depends_on and are only reachable through gate routing.
Use support phases for specialized remediation: a git-resolver that fixes merge conflicts, a security-fixer that patches vulnerabilities, a fixer that addresses gate feedback.
Per-Phase Agent Override
Section titled “Per-Phase Agent Override”By default, every phase uses the runtime’s default agent. The agent field overrides this for a specific phase:
- name: security-audit type: standard depends_on: [developer] agent: security-scannerThe value must be a built-in agent name or an agent declared in the team’s agents section. See Cliq SDK for details on choosing and configuring agents.
Re-Run Behavior
Section titled “Re-Run Behavior”When cliq run ends in an escalation or failure, you don’t need to re-run cliq req — the requirement hasn’t changed. Fix the issue and run again.
| Scenario | What happens |
|---|---|
| Early escalation — first gate fails before any agent did work | cliq run silently cleans prior artifacts and proceeds |
| Mid-pipeline failure — some agents completed phases | cliq run warns which phases completed and asks for confirmation |
| Successful completion — pipeline finished cleanly | cliq run refuses. Start a new task with cliq req |
cliq run # auto-cleans if no agents did real workcliq run -f # force re-run, skip confirmationValidation
Section titled “Validation”cliq team validate checks your workflow for structural correctness. See team.yml Reference — Validation Rules for the full list of checks and error messages.
Key rules:
- Every phase must have
nameandtype - No duplicate phase names, no cycles in
depends_on, at least one root phase - Phase names cannot contain
.characters - Phases with
agent: execmust have commands and nomax_iterations - Gate phases with
agent: hugmust have areview:block withreviewer; thereview:block is not allowed on other configurations - Team phases must have a
teamfield; theteamfield is not allowed on other types - Every phase (except
agent: exec) must have a matchingroles/<name>.md(including team phases)
Examples
Section titled “Examples”Simple sequential
Section titled “Simple sequential”workflow: phases: - name: architect type: standard - name: developer type: standard depends_on: [architect] - name: reviewer type: gate depends_on: [developer] commands: - name: tests run: npm test max_iterations: 3Parallel fan-out and fan-in
Section titled “Parallel fan-out and fan-in”workflow: phases: - name: architect type: standard - name: tester type: standard depends_on: [architect] - name: security-auditor type: standard depends_on: [architect] - name: developer type: standard depends_on: [tester, security-auditor] - name: reviewer type: gate depends_on: [developer] commands: - name: build run: npm run build - name: tests run: npm test max_iterations: 3Composing teams
Section titled “Composing teams”workflow: phases: - name: architect type: standard
- name: developer type: standard depends_on: [architect]
- name: security-audit type: team depends_on: [developer] team: "@acme/security-scan" inputs: scan_target: src/
- name: reviewer type: gate depends_on: [security-audit] commands: - name: tests run: npm test max_iterations: 3Here, the security audit is handled by a separate team (@acme/security-scan) that runs its own multi-agent pipeline. The reviewer gate downstream receives the security audit’s results through a normal channel handoff — the team agent collects the sub-team’s task board and channel outputs and writes them as a standard handoff.
Full pipeline with all phase types
Section titled “Full pipeline with all phase types”workflow: phases: - name: fetch-data type: standard agent: gdrive action: get sources: - name: source-docs ref: "$(inputs.folder_id)"
- name: architect type: standard depends_on: [fetch-data]
- name: developer type: standard depends_on: [architect]
- name: tester type: standard depends_on: [architect] agent: test-specialist
- name: reviewer type: gate depends_on: [developer, tester] commands: - name: build run: npm run build scope: repo if: "test -f package.json" - name: tests run: npm test scope: repo if: "test -f package.json" max_iterations: 3
- name: git-finalize type: standard depends_on: [reviewer] agent: git action: create_pr
- name: git-verify type: standard agent: exec depends_on: [git-finalize] commands: - name: pushed run: "git ls-remote --heads origin $(git branch --show-current) | grep -q ."
- name: publish type: standard depends_on: [git-verify] agent: gdrive action: create target_entries: - name: summary file: reports/summary.md ref: "$(inputs.output_folder)"
support: - name: git-resolver type: standard - name: hotfix-dev type: standard