Full plan-to-merged-PR pipeline with checkpoint framework, QA phases, and multi-agent orchestration. Use when running end-to-end from plan to merge, resuming an interrupted arc with --resume after a crash or session end, or when any named phase fails (forge, work, code-review, mend, test, ship, merge, etc. — see body for full phase list). Keywords: arc, pipeline, --resume, checkpoint, convergence, forge, mend, ship, merge.
Scanned 5/28/2026
Install to Claude Code
npx -y skills add vinhnxv/rune --skill arc --agent claude-codeInstalls into .claude/skills of the current project.
Are you the author of Arc?
Add the live security badge to your README — it updates automatically with every re-scan.
[](https://www.skillsdirectory.com/skills/vinhnxv-arc)More formats (shields.io, HTML) on the badges page.
---
name: arc
description: |
Full plan-to-merged-PR pipeline with checkpoint framework, QA phases, and
multi-agent orchestration. Use when running end-to-end from plan to merge,
resuming an interrupted arc with --resume after a crash or session end, or
when any named phase fails (forge, work, code-review, mend, test, ship,
merge, etc. — see body for full phase list).
Keywords: arc, pipeline, --resume, checkpoint, convergence, forge, mend,
ship, merge.
user-invocable: true
disable-model-invocation: false
argument-hint: "[plan-file-path | --resume | --quick-mode \"<prompt|plan-path>\" [--force]]"
allowed-tools:
- Read
- Write
- Edit
- Bash
- Glob
- Grep
- Agent
- TaskCreate
- TaskUpdate
- TaskGet
- TaskList
- TeamCreate
- TeamDelete
- SendMessage
- AskUserQuestion
- EnterPlanMode
- ExitPlanMode
---
# /rune:arc — End-to-End Orchestration Pipeline
Chains 19 phases into a single automated pipeline (v3.0.0-alpha.6 — was 30 pre-alpha.2; goldmask + bot-review + PR-comment resolution moved out of the default order; Day 5 alpha.6 absorbed plan_refine, drift_review, inspect_fix, verify_inspect, verify_mend, pre_ship_validation into their parents and removed deploy_verify). Each phase runs as its own Claude Code turn with fresh context — the `arc-phase-stop-hook.sh` drives phase iteration via the Stop hook pattern. Artifact-based handoff connects phases. Checkpoint state enables resume after failure.
**Context budget advisory**: Full arc run: 19 phases x ~3.7min avg = ~70 minutes (lower bound). Context compaction is almost guaranteed in a single session. For constrained sessions, use `--no-forge` to skip Phase 1 enrichment, or split into multiple `/rune:arc --resume` sessions. For context optimization, use `--step-groups` to pause at group boundaries — each group gets a fresh context window on resume. The `PreCompact` hook saves checkpoint state automatically.
**Load skills**: `roundtable-circle`, `context-weaving`, `rune-orchestration`, `elicitation`, `team-sdk`, `testing`
## CRITICAL — No Pipeline Second-Guessing (ARC-NSG-001)
When the user invokes `/rune:arc` without `--quick-mode`, **execute the full arc pipeline immediately**. Do NOT:
- Present options like "the quick mode might be better for this"
- Ask "are you sure?" or "before I commit N hours..."
- Recommend a different pipeline based on plan size, effort estimates, or PR strategy
- Second-guess the user's choice by analyzing plan complexity first
The user chose `/rune:arc` deliberately. Respect that choice. If the plan is small, arc still works — it just finishes faster. If the user wanted the lightweight 4-phase path, they would have invoked `/rune:arc --quick-mode`.
**Exception**: The `--confirm` flag explicitly opts into a pause on all-CONCERN escalation. That is the ONLY confirmation point in the pipeline.
## CRITICAL — Agent Teams Enforcement (ATE-1)
**EVERY phase that summons agents MUST follow this exact pattern. No exceptions.**
```
1. TeamCreate({ team_name: "{phase-prefix}-{id}" }) ← CREATE TEAM FIRST
2. TaskCreate({ subject: ..., description: ... }) ← CREATE TASKS
3. Agent({ team_name: "...", name: "...", ← SPAWN WITH team_name
subagent_type: "general-purpose", ← ALWAYS general-purpose
prompt: "You are {agent-name}...", ... }) ← IDENTITY VIA PROMPT
4. Monitor → Shutdown → TeamDelete with fallback ← CLEANUP
```
**NEVER DO:**
- `Agent({ ... })` without `team_name` — bare Agent calls bypass Agent Teams entirely.
- Using named `subagent_type` values — always use `subagent_type: "general-purpose"` and inject agent identity via the prompt.
**ENFORCEMENT:** The `enforce-teams.sh` PreToolUse hook blocks bare Agent calls when a Rune workflow is active.
## Phase Number → Name Mapping
The pipeline uses **named phases** (not numeric IDs) in `PHASE_ORDER`. The numeric labels below are for human reference only — execution order is always determined by position in `PHASE_ORDER`.
| # | Exec Order | Phase Key | Type | Timeout | Delegated To |
|---|-----------|-----------|------|---------|-------------|
| 1 | 1 | `forge` | Team | 15 min | `/rune:forge` |
| 1.1 | 2 | `forge_qa` | Team | 5 min | QA gate (1 agent) |
| 2 | 3 | `plan_review` | Team | 15 min | `/rune:appraise` (inspect mode); absorbs the former `plan_refine` sub-step (v3.0.0-alpha.6 C4a) |
| 2.7 | 4 | `verification` | Inline | 30 sec | — |
| 5 | 5 | `work` | Team | 35 min | `/rune:strive`; absorbs the former `drift_review` sub-step (v3.0.0-alpha.6 C4b) |
| 5.01 | 6 | `work_qa` | Team | 5 min | QA gate (1 agent) |
| 5.9 | 7 | `inspect` | Team | 45 min | `/rune:inspect` (4 Inspector Ashes) — unified plan-vs-implementation engine. Sub-steps: STEP A deterministic pre-checks (absorbed `gap_analysis` STEP A v3.0.0-alpha.7 Day 6), STEP 1-4 audit, STEP 4.5 halt-gate with Task Completion Gate + plan writeback (absorbed `gap_analysis` STEP D), STEP 5 gap-fixer dispatch (absorbed `inspect_fix` C4c + `gap_remediation` Day 6), STEP 6 convergence (absorbed `verify_inspect` C4c). |
| 6 | 8 | `code_review` | Team | 15 min | `/rune:appraise --deep` |
| 6.1 | 9 | `code_review_qa` | Team | 5 min | QA gate (1 agent) |
| 6.6 | 10 | `verify` | Team | 10 min | Finding verification gate |
| 7 | 11 | `mend` | Team | 23 min | `/rune:mend` |
| 7.01 | 12 | `mend_qa` | Team | 9 min | QA gate (1 agent) + runMendQAConvergence post-step (absorbed `verify_mend` v3.0.0-alpha.6 C4d) |
| 7.7 | 13 | `test` | Team | 25-50 min | Testing agents |
| 7.71 | 14 | `test_qa` | Team | 5 min | QA gate (1 agent) |
| 9 | 15 | `ship` | Inline | 11 min | preShipValidator pre-step (absorbed `pre_ship_validation` v3.0.0-alpha.6 C4e) + PR creation; `deploy_verify` removed |
| 9.5 | 16 | `merge` | Inline | 10 min | — |
> **Execution order**: The "Exec Order" column shows the actual sequence (1–16). Phase numbers (#) are for human reference only — always use `PHASE_ORDER` array position. Total: 16 default phases (v3.0.0-alpha.7 Day 6 absorbed gap_analysis + gap_analysis_qa + gap_remediation into inspect; v3.0.0-alpha.6 Day 5 absorbed plan_refine→plan_review, drift_review→work, inspect_fix+verify_inspect→inspect, verify_mend→mend_qa post-step, pre_ship_validation→ship; deploy_verify removed entirely. Prior history: v3.0.0-alpha.2 cut goldmask_verification, goldmask_correlation, bot_review_wait, pr_comment_resolution; alpha.1 cut design_*, semantic_verification, task_decomposition, test_coverage_critique, release_quality_check, browser_test*, storybook_verification, ux_verification).
## Usage
```
/rune:arc <plan_file.md> # Full pipeline
/rune:arc <plan_file.md> --no-forge # Skip research enrichment
/rune:arc <plan_file.md> --approve # Require human approval for work tasks
/rune:arc --resume # Resume from last checkpoint
/rune:arc <plan_file.md> --skip-freshness # Skip freshness validation
/rune:arc <plan_file.md> --confirm # Pause on all-CONCERN escalation
/rune:arc <plan_file.md> --no-pr # Skip PR creation (Phase 9)
/rune:arc <plan_file.md> --no-merge # Skip auto-merge (Phase 9.5)
/rune:arc <plan_file.md> --draft # Create PR as draft
/rune:arc <plan_file.md> --no-accept-external # Prompt when unrelated changes detected (default: accept)
/rune:arc <plan_file.md> --step-groups # Pause at each phase group boundary
/rune:arc --quick-mode "<prompt|plan-path>" [--force] # Lightweight 4-phase pipeline
```
## Flags
| Flag | Description | Default |
|------|-------------|---------|
| `--no-forge` | Skip Phase 1 (research enrichment), use plan as-is | Off |
| `--approve` | Require human approval for each work task (Phase 5 only) | Off |
| `--resume` | Resume from last checkpoint. Plan path auto-detected from checkpoint | Off |
| `--skip-freshness` | Skip plan freshness check (bypass stale-plan detection) | Off |
| `--confirm` | Pause for user input when all plan reviewers raise CONCERN verdicts | Off |
| `--no-pr` | Skip Phase 9 (PR creation) | Off |
| `--no-merge` | Skip Phase 9.5 (auto merge) | Off |
| `--no-test` | Skip Phase 7.7 (testing) | Off |
| `--draft` | Create PR as draft | Off |
| `--accept-external` | Accept external changes (bug fixes, audit commits) on branch without prompting | **On** |
| `--no-accept-external` | Prompt user when unrelated changes are detected on branch | Off |
| `--step-groups` | Pause at each phase group boundary for context optimization | Off |
| `--status` | Show current arc phase, progress, and elapsed time (delegates to rune-status.sh) | Off |
| `--quick-mode` | Lightweight 4-phase pipeline (plan → work+evaluate → review → mend). Skips checkpoint init and PHASE_ORDER dispatch — runs as a single-turn delegation chain. See [arc-quick-mode.md](references/arc-quick-mode.md) | Off |
| `--force` | (`--quick-mode` only) Skip the complexity gate warning on plans with 8+ tasks | Off |
> **Note**: Worktree mode for `/rune:strive` (Phase 5) is activated via `work.worktree.enabled: true` in talisman.yml, not via a `--worktree` flag on arc.
## External Changes Policy (`accept_external_changes`)
When `--accept-external` is passed (or `arc.defaults.accept_external_changes: true` in talisman), the pipeline tolerates commits on the working branch that are NOT part of the plan. This is common when:
- Running `/rune:arc-batch` where prior arcs leave commits on the branch
- Running `/rune:audit` or manual bug fixes in a parallel session that commit to the same branch
- Cherry-picking hotfixes onto the arc's working branch
**Behavior when enabled:**
- Do NOT pause or prompt the user about unrelated changes — continue autonomously
- Gap analysis evaluates only plan criteria coverage; external changes are not flagged as drift
- Code review reviews all changes but does not halt for code outside plan scope
- All commits (plan-related and external) are included in the PR
**Default**: `true` (accept external changes silently). Use `--no-accept-external` or `arc.defaults.accept_external_changes: false` to restore the prompting behavior.
## Workflow Lock (writer)
```javascript
const lockConflicts = Bash(`cd "${CWD}" && source plugins/rune/scripts/lib/workflow-lock.sh && rune_check_conflicts "writer"`)
if (lockConflicts.includes("CONFLICT")) {
AskUserQuestion({ question: `Active workflow conflict:\n${lockConflicts}\nProceed anyway?` })
}
Bash(`cd "${CWD}" && source plugins/rune/scripts/lib/workflow-lock.sh && rune_acquire_lock "arc" "writer"`)
```
## Pre-flight
See [arc-preflight.md](references/arc-preflight.md) for the full pre-flight sequence.
Read and execute the arc-preflight.md algorithm at dispatcher init.
### Plan Freshness Check (FRESH-1)
See [freshness-gate.md](references/freshness-gate.md) for the full algorithm.
Read and execute the algorithm. Store `freshnessResult` for checkpoint initialization below.
### Context Monitoring Bridge Check (non-blocking advisory)
```javascript
const bridgePattern = `/tmp/rune-ctx-*.json`
const bridgeFiles = Bash(`ls ${bridgePattern} 2>/dev/null | head -1`).trim()
if (!bridgeFiles) {
warn(`Context monitoring bridge not detected.`)
}
const ctxBridgeFile = bridgeFiles || null
```
### Phase Constants
Read [arc-phase-constants.md](references/arc-phase-constants.md) for PHASE_ORDER, PHASE_TIMEOUTS, CYCLE_BUDGET, calculateDynamicTimeout(), FORBIDDEN_PHASE_KEYS, and updateCascadeTracker().
### Initialize Checkpoint (ARC-2)
See [arc-checkpoint-init.md](references/arc-checkpoint-init.md) for the full initialization.
Read and execute the arc-checkpoint-init.md algorithm.
### Inter-Phase Cleanup Guard (ARC-6)
See [arc-preflight.md](references/arc-preflight.md) for `prePhaseCleanup()`.
```javascript
Read(references/arc-preflight.md)
Read(references/arc-phase-cleanup.md)
```
### Stale Arc Team Scan
See [arc-preflight.md](references/arc-preflight.md) for the stale team scan algorithm.
## Status (`--status`)
Early return — display current arc phase, progress, and elapsed time without entering the pipeline.
```javascript
if (args.includes("--status")) {
const output = Bash(`"${RUNE_PLUGIN_ROOT}/scripts/rune-status.sh"`)
// Display current phase, elapsed time, completed/total phases
return output
}
```
## Quick Mode (`--quick-mode`)
Early return — runs the lightweight 4-phase pipeline (plan → work+evaluate → review → mend) as a single-turn delegation chain. Skips checkpoint init and PHASE_ORDER dispatch entirely. Mirrors the `--status` early-return pattern above so quick-mode never touches the full-pipeline state machine.
```javascript
if (args.includes("--quick-mode")) {
// Read and execute the arc-quick-mode.md algorithm.
// The branch is fully self-contained — devise/strive/appraise/mend each manage
// their own teams; arc neither creates a checkpoint nor invokes the stop hook.
Read(references/arc-quick-mode.md)
return // Do not fall through to checkpoint init or PHASE_ORDER dispatch
}
```
## Resume (`--resume`)
See [arc-resume.md](references/arc-resume.md) for the full resume algorithm.
```javascript
if (args.includes("--resume")) {
Read(references/arc-preflight.md)
Read(references/arc-phase-cleanup.md)
Read and execute the arc-resume.md algorithm.
}
```
## Pre-Flight: State File Conflict Detection
Enforces ONE arc at a time — checks for existing state files from previous or concurrent sessions. Handles 6 cases (F1-F6) including hard blocks, resume prompts, and stale cleanup.
See [arc-state-conflict.md](references/arc-state-conflict.md) for the full conflict detection algorithm and case table.
## Phase Loop State File
**Co-located with checkpoint init (v2.6.0)**: The phase loop state file is now written as part of [arc-checkpoint-init.md](references/arc-checkpoint-init.md), immediately after the checkpoint `Write()` call. This eliminates the "missing state file" bug where the LLM wrote the checkpoint but skipped this step under context pressure.
If you are here during execution, the state file (`.rune/arc-phase-loop.local.md`) should already exist. If it does not, the safety guard in "First Phase Invocation" below will catch and recover.
See [arc-phase-loop-state.md](references/arc-phase-loop-state.md) for the state file schema reference.
## Discipline Integration
Integrates at 3 points: **Phase 5** (work loop with AC criteria), **Phase 8.5** (SCR/proof metrics), **Post-Arc** (echo persist). Config: `discipline.enabled` (default: true), `discipline.block_on_fail` (default: false). See `strive/references/discipline-work-loop.md` and `discipline/references/metrics-schema.md`.
### Blind AC Verification (Phase 5 — strive-internal)
When `blind_verification.enabled: true` in talisman, strive Phase 4.6 runs a blind AC verification gate within the work phase. A blind-validation-agent receives ONLY the plan's acceptance criteria and the committed code — no worker context, no task files, no implementation notes. This is NOT a separate arc phase; it runs inside `/rune:strive` as a quality gate before Phase 5 (echo persist). Config: `blind_verification.model` (default: `"sonnet"`), `blind_verification.fail_on_partial` (default: `false`), `blind_verification.max_remediation` (default: `1`), `blind_verification.timeout_ms` (default: `120000`).
## QA Discipline Protocol
Independent QA gates enforce quality obligations at every gated phase. The Tarnished (orchestrator) and all phase agents MUST adhere to these 6 obligations:
1. **No self-evaluation**: The Tarnished MUST NOT evaluate its own phase output. QA agents are spawned as independent teammates with read-only access to phase artifacts. QA verdicts cannot be overridden programmatically.
2. **Verdict file contract**: Every QA gate MUST produce a verdict JSON file at `tmp/arc/{id}/qa/{phase}-verdict.json` before the stop hook advances. Missing verdict files default to FAIL with `timed_out: true`.
3. **GUARD 9 retry budget**: QA retries are capped at `MAX_QA_RETRIES` (2), which MUST remain strictly less than `MAX_PHASE_DISPATCHES - 1` (currently 3). Exceeding this invariant triggers GUARD 9 destruction of the state file. Do NOT increase `MAX_QA_RETRIES` without first raising `MAX_PHASE_DISPATCHES` in the stop hook.
4. **Score transparency**: All QA scores (artifact, quality, completeness, overall) are persisted in verdict files and surfaced in the QA Dashboard (`tmp/arc/{id}/qa/dashboard.md`). No phase may suppress or alter QA scores after they are written.
5. **Human escalation**: When QA fails after max retries, the pipeline MUST escalate to the human via `AskUserQuestion` — never silently skip or auto-pass a failed gate.
6. **Dashboard generation**: After the last QA-gated phase completes, `generateQADashboard(arcId)` MUST be called to produce the consolidated pipeline quality summary. The dashboard is injected into the PR body (Phase 9) for reviewer visibility.
See [arc-phase-qa-gate.md](references/arc-phase-qa-gate.md) for the full QA gate architecture, scoring system, and per-phase checklists.
## First Phase Invocation
Execute the first pending phase from the checkpoint. The Stop hook (`arc-phase-stop-hook.sh`) handles all subsequent phases automatically.
**CRITICAL — Single-Phase-Per-Turn Rule**: You MUST execute exactly ONE phase per turn, then STOP responding. Do NOT batch-process multiple phases in a single turn. Do NOT skip conditional phases (semantic_verification, task_decomposition) based on assumptions — each phase has its own gate logic in its reference file that MUST be executed. The Stop hook advances to the next phase automatically. Violating this rule causes phases to be skipped without proper gate evaluation.
```javascript
// ── SAFETY GUARD: Verify phase loop state file exists before first phase ──
// FIX (v2.6.0): Catches the case where checkpoint init completed but state file
// write was skipped (context pressure, LLM shortcutting, or error between steps).
// Without this file, the Stop hook silently exits 0 and the arc stalls after Phase 1.
const stateFilePath = '.rune/arc-phase-loop.local.md'
const stateFileExists = Bash(`test -f "${stateFilePath}" && echo "ok" || echo "missing"`).trim()
if (stateFileExists !== 'ok') {
warn('RECOVERY: Phase loop state file missing — recreating from checkpoint.')
// Reconstruct from checkpoint data (checkpoint was written successfully)
const cp = JSON.parse(Read(checkpointPath))
const recoverySessionId = "${CLAUDE_SESSION_ID}" || Bash('echo "${RUNE_SESSION_ID:-}"').trim() || 'unknown'
const recoveryBranch = Bash("git branch --show-current 2>/dev/null").trim() || 'main'
const recoveryOwnerPid = Bash('echo $PPID').trim()
// ── INTEG-RECOVERY validation (v2.29.8): Validate checkpoint fields before propagating ──
// BUG FIX: If checkpoint has corrupt config_dir (e.g., tmp/arc/...), the recovery path
// would propagate the corruption to the new state file, bypassing all 3 layers of validation.
// Resolve config_dir from CLAUDE_CONFIG_DIR directly — do NOT trust checkpoint's config_dir.
const recoveryConfigDir = Bash('cd "${CLAUDE_CONFIG_DIR:-$HOME/.claude}" 2>/dev/null && pwd -P').trim()
if (!recoveryConfigDir || recoveryConfigDir.startsWith('tmp/') || recoveryConfigDir.includes('/tmp/arc/')) {
throw new Error(`FATAL (INTEG-RECOVERY-001): Resolved config_dir "${recoveryConfigDir}" is invalid. Cannot recover state file.`)
}
if (!recoveryOwnerPid || !/^\d+$/.test(recoveryOwnerPid)) {
throw new Error(`FATAL (INTEG-RECOVERY-002): owner_pid "${recoveryOwnerPid}" is invalid.`)
}
if (recoverySessionId === 'unknown') {
throw new Error(`FATAL (INTEG-RECOVERY-003): session_id is unknown — cannot recover state file without session identity.`)
}
if (!cp.plan_file || cp.plan_file === 'null') {
throw new Error(`FATAL (INTEG-RECOVERY-004): checkpoint.plan_file is empty/null — cannot recover.`)
}
// Warn if checkpoint config_dir was corrupt (the bug we're fixing)
if (cp.config_dir && (cp.config_dir.startsWith('tmp/') || cp.config_dir.includes('/tmp/arc/'))) {
warn(`INTEG-RECOVERY: Checkpoint had corrupt config_dir="${cp.config_dir}" — using fresh resolution "${recoveryConfigDir}" instead.`)
}
const recoveryContent = `---
active: true
iteration: 0
max_iterations: 66
checkpoint_path: ${checkpointPath}
plan_file: ${cp.plan_file}
branch: ${recoveryBranch}
arc_flags: ${(cp.flags?.no_forge ? '--no-forge ' : '') + (cp.flags?.approve ? '--approve ' : '') + (cp.flags?.no_test ? '--no-test ' : '')}
config_dir: ${recoveryConfigDir}
owner_pid: ${recoveryOwnerPid}
session_id: ${recoverySessionId}
compact_pending: false
user_cancelled: false
cancel_reason: null
cancelled_at: null
stop_reason: null
---
`
Write(stateFilePath, recoveryContent)
// Post-write verification (same pattern as arc-checkpoint-init.md)
const recoveryVerifyConfigDir = Bash('grep "^config_dir:" .rune/arc-phase-loop.local.md | sed "s/^config_dir: //"').trim()
if (recoveryVerifyConfigDir !== recoveryConfigDir) {
throw new Error(`FATAL (INTEG-RECOVERY-POST): Written config_dir "${recoveryVerifyConfigDir}" ≠ expected "${recoveryConfigDir}".`)
}
log('Phase loop state file recovered successfully.')
}
// Check for context-critical shutdown signal before starting next phase (Layer 1)
const shutdownSignalCheck = (() => {
try {
const sid = "${CLAUDE_SESSION_ID}" || Bash(`echo "\${RUNE_SESSION_ID:-}"`).trim()
const signalPath = `tmp/.rune-shutdown-signal-${sid}.json`
const signal = JSON.parse(Read(signalPath))
return signal?.signal === "context_warning"
} catch { return false }
})()
if (shutdownSignalCheck) {
warn("CTX-WARNING: Context pressure detected between phases. Skipping remaining phases.")
// Mark remaining phases as skipped in checkpoint
for (const p of PHASE_ORDER) {
if (checkpoint.phases[p]?.status === 'pending') {
checkpoint.phases[p].status = 'skipped'
checkpoint.phases[p].skip_reason = 'context_pressure'
}
}
Write(checkpointPath, checkpoint)
return
}
// Find first pending phase
const firstPending = PHASE_ORDER.find(p => checkpoint.phases[p]?.status === 'pending')
if (!firstPending) {
log("All phases already complete. Nothing to execute.")
return
}
// Schema v19: stamp phase start time before executing
checkpoint.phases[firstPending].started_at = new Date().toISOString()
Write(checkpointPath, checkpoint)
// Read and execute the phase reference file
const refFile = getPhaseReferenceFile(firstPending)
Read(refFile)
// Execute the phase algorithm as described in the reference file.
// When done, update checkpoint.phases[firstPending].status to "completed".
// Schema v19: stamp phase completion time and compute duration
const completionTs = Date.now()
checkpoint.phases[firstPending].completed_at = new Date(completionTs).toISOString()
const phaseStartMs = new Date(checkpoint.phases[firstPending].started_at).getTime()
checkpoint.totals = checkpoint.totals ?? { phase_times: {}, total_duration_ms: null, cost_at_completion: null }
const phaseDuration = completionTs - phaseStartMs
checkpoint.totals.phase_times[firstPending] = Number.isFinite(phaseDuration) && phaseDuration >= 0
? phaseDuration : null
// Then STOP responding — the Stop hook will advance to the next phase.
```
**Phase-to-reference mapping**: See `arc-phase-stop-hook.sh` `_phase_ref()` function for the canonical phase → reference file mapping.
**Timing instrumentation**: Each phase MUST stamp `started_at` before execution and `completed_at` + `totals.phase_times[phaseName]` (duration in ms) after. The Stop hook re-injects this same pattern for all subsequent phases via the phase prompt template. The `totals.phase_times` map accumulates durations across the full pipeline.
## Spec Continuity (Plan Path Propagation)
The `plan_file` path written to the phase loop state file and checkpoint is propagated to downstream phases that need the original plan specification as their source-of-truth. Each phase reference file reads `plan_file` from the checkpoint before spawning agents.
| Phase | Checkpoint Key | Purpose |
|-------|---------------|---------|
| `plan_review` (Phase 2) | `plan_file_path` → review agents | Reviewers read plan to evaluate scope and detect drift |
| `inspect` (Phase 5.9, STEP A + STEP D) | `plan_file_path` → STEP A deterministic checks + STEP D halt-gate | v3.0.0-alpha.7 Day 6: absorbed gap_analysis flow. STEP A extracts acceptance criteria + cross-references committed files; STEP D applies Task Completion Gate (PR #310 floor) and writes Implementation Status appendix back to the plan |
| `test` (Phase 7.7) | `plan_file_path` → test agents | Test agents derive coverage targets from plan requirements |
| `ship` (Phase 9, STEP -0.5) | `plan_file_path` → preShipValidator | Pre-ship gate (absorbed `pre_ship_validation` v3.0.0-alpha.6 C4e) reads plan to verify all stated criteria are met before PR |
**Rule**: Phases that consume `plan_file_path` MUST read it from `checkpoint.plan_file` (not from the state file or flags). Workers receive it as `planFilePath` in their context prompt so they can cross-reference the original spec, even when the pipeline spans multiple sessions via `--resume`.
## Post-Arc (Final Phase)
**MANDATORY**: These steps run after Phase 9.5 MERGE (the last phase). The Stop hook injects a completion prompt when all phases are done. You MUST read and execute `arc-phase-completion-stamp.md` and `post-arc.md` — do NOT skip them or just present a summary. The plan file update is the primary deliverable of this phase.
### Timing Totals + Completion Stamp (schema v19)
Before calling the Plan Completion Stamp, record arc-level timing metrics:
```javascript
// Schema v19: record arc completion time and total duration
const completedAtTs = new Date().toISOString()
checkpoint.completed_at = completedAtTs
checkpoint.totals = checkpoint.totals ?? { phase_times: {}, total_duration_ms: null, cost_at_completion: null }
const totalDuration = Date.now() - new Date(checkpoint.started_at).getTime()
if (!Number.isFinite(totalDuration) || totalDuration < 0) {
warn(`Arc timing anomaly: computed duration ${totalDuration}ms — setting to null`)
checkpoint.totals.total_duration_ms = null
} else {
checkpoint.totals.total_duration_ms = totalDuration
}
// Read cost from statusline bridge file (non-blocking — skip if unavailable)
if (ctxBridgeFile) {
try {
const bridge = JSON.parse(Bash(`cat "${ctxBridgeFile}" 2>/dev/null`))
checkpoint.totals.cost_at_completion = bridge.cost ?? null
} catch (e) { /* bridge unavailable — leave null */ }
}
Write(checkpointPath, checkpoint)
```
### Plan Completion Stamp
See [arc-phase-completion-stamp.md](references/arc-phase-completion-stamp.md). Runs FIRST after merge — writes persistent record before context-heavy steps.
### Result Signal (automatic)
Written automatically by `arc-result-signal-writer.sh` PostToolUse hook. No manual call needed. See [arc-result-signal.md](references/arc-result-signal.md).
### Completion Report
See [post-arc.md](references/post-arc.md) for the completion report template.
> **Echo persist removed**: v3.0.0-alpha.1 removed the persistent memory layer
> (no rune-echoes skill, no `.rune/echoes/` runtime consumer). Post-arc no longer
> writes echoes — agent output is now ephemeral (`tmp/`).
### Proof Manifest Persistence (Discipline Integration, v1.173.0)
Persists the proof manifest (SCR per criterion) as a PR comment after ship/merge. Uses `--body-file` for injection-safe PR comments.
See [arc-proof-manifest.md](references/arc-proof-manifest.md) for the full manifest schema and persistence logic.
### Lock Release
```javascript
Bash(`cd "${CWD}" && source plugins/rune/scripts/lib/workflow-lock.sh && rune_release_all_locks`)
```
### Final Sweep (ARC-9) + Response Completion
See [post-arc.md](references/post-arc.md). 30-second budget. After sweep, **finish your response immediately** — IGNORE zombie teammate messages (Stop hook handles cleanup).
## References
- [Architecture & Pipeline Overview](references/arc-architecture.md) — Pipeline diagram, orchestrator design, transition contracts
- [Phase Constants](references/arc-phase-constants.md) — PHASE_ORDER, PHASE_TIMEOUTS, CYCLE_BUDGET, shared utilities
- [Quick Mode](references/arc-quick-mode.md) — `--quick-mode` 4-phase pipeline (plan → work+eval → review → mend)
- [Failure Policy](references/arc-failure-policy.md) — Per-phase failure handling matrix
- [Checkpoint Init](references/arc-checkpoint-init.md) — Schema v28, 3-layer config resolution
- [Resume](references/arc-resume.md) — Checkpoint restoration, schema migration
- [Pre-flight](references/arc-preflight.md) — Git state, branch creation, stale team scan, prePhaseCleanup
- [Phase Cleanup](references/arc-phase-cleanup.md) — postPhaseCleanup, PHASE_PREFIX_MAP
- [Freshness Gate](references/freshness-gate.md) — 5-signal plan drift detection
- [Phase Tool Matrix](references/phase-tool-matrix.md) — Per-phase tool restrictions and time budgets
- [Delegation Checklist](references/arc-delegation-checklist.md) — Phase delegation contracts (RUN/SKIP/ADAPT)
- [Naming Conventions](references/arc-naming-conventions.md) — Gate/validator/sentinel/guard taxonomy
- [Post-Arc](references/post-arc.md) — Echo persist, completion report, ARC-9 sweep
- [Completion Stamp](references/arc-phase-completion-stamp.md) — Plan file completion record
- [Result Signal](references/arc-result-signal.md) — Deterministic completion signal for stop hooks
- [Stagnation Sentinel](references/stagnation-sentinel.md) — Error pattern detection, budget enforcement
- [State Conflict Detection](references/arc-state-conflict.md) — Pre-flight F1-F6 conflict cases
- [Phase Loop State](references/arc-phase-loop-state.md) — State file template for Stop hook driver
- [Proof Manifest](references/arc-proof-manifest.md) — Discipline proof manifest persistence (v1.173.0)
Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.
No comments yet. Be the first to comment!