SuperAPI AI Directory

maestro-ralph

General & other

View repository

Updated 10-15 20:11

About this skill

Notation

Skill(name) / Skill(name, args) = load ~/.codex/skills/{name}/SKILL.md or .codex/skills/{name}/SKILL.md(project overrides global), args fill the input parameter slots of the target SKILL.md <context> block. This is an internal call between skills,not a CLI command. Strictly forbidden to translate as Bash("maestro {name} {args}")— the CLI does not accept bare intent.

Valid CLI subcommands are limited to structured operations:maestro ralph next、maestro ralph complete、maestro ralph skills、maestro delegate、maestro explore , etc.

Session

.workflow/.maestro/{session_id}/status.json — single source of truth for the workflow (schema see <appendix>). session_id format:ralph-{YYYYMMDD-HHmmss}(created by this skill, adaptive chain) or maestro-{YYYYMMDD-HHmmss}(Skill(maestro) created by the coordinator, static chain). Both types are advanced by Skill(maestro-ralph-execute) . When session-id is omitted: continue/execute take the latest status=="running"; status takes the latest session (by created_at, regardless of status).

Entry points

  • Skill(maestro-ralph, "intent") — create new session: infer → decompose → build → create_goal (if there is a decomposition) → dispatch ralph-execute
  • Skill(maestro-ralph, "continue [session-id]") — user entry point: resume execution, route to S_DISPATCH → Skill(maestro-ralph-execute). When session-id is omitted, take the latest status=="running" session
  • Skill(maestro-ralph, "status [session-id]") — display progress. When session-id is omitted, take the latest session (by created_at, regardless of status)

continue vs ralph-execute: when the user says "continue", go through Skill(maestro-ralph, "continue")(user entry point, via S_DISPATCH handoff); the internal step advancement chain and decision callbacks go through Skill(maestro-ralph-execute)(internal handoff, skipping the ralph routing layer). Both ultimately execute the step via ralph-execute.

Advancement rules:step advancement is handled by Skill(maestro-ralph-execute) is responsible; ralph only intervenes during build / decision evaluation. Decision nodes are automatically handled by ralph-execute Skill(maestro-ralph) directly calling handoff, with no need for the user to switch manually.

CLI vs Skill boundary:maestro as a CLI binary only has structured subcommands (ralph、delegate、explore , etc.), and does not accept bare intent.Bash("maestro \"some intent\"") will error out and exit. Creating sessions and routing intent must be done through Skill(maestro-ralph) or Skill(maestro) skill calls. The CLI layer is only used for step loading (ralph next) and completion marking (ralph complete)。

Initial decomposition (S_DECOMPOSE): boundary-clarified via ≤3 questions for broad intents (重构/全面/迁移/重写). Write to status.json's boundary_contract / execution_criteria / task_decomposition, register the goal via create_goal .

Step kinds:

  • Execute step: ralph-execute calls Bash("maestro ralph next") to load SKILL.md + required_reading in full, and executes inline according to stdout
  • decision step: step.decision field is non-empty; return to ralph for evaluation (CLI is read-only analysis)

Key difference from maestro coordinator:

  • maestro: static chain → one-time selection → runs all steps
  • ralph: living chain → decision nodes re-evaluate → chain grows/shrinks dynamically

Session: .workflow/.maestro/ralph-{YYYYMMDD-HHmmss}/status.json Mutual invocation with Skill(maestro-ralph-execute) forms a self-perpetuating work loop.

Execution Flow

 Skill(maestro-ralph, "intent") ─▶ ralph        infer → decompose → build chain
                              │           resolves command_path per step
                              │           writes status.json
                              │           calls create_goal
                              ▼
                       ralph-execute  ◀─┐ 执行 step → `maestro ralph next` + inline + `ralph complete`
                              │         │ decision step → Skill(maestro-ralph)
                              └─────────┘ CLI writes step.completion_confirmed
                       loop until all completion_confirmed | paused

<deferred_reading>

  • ralph-amend-goal.md — read when --amend flag active for goal amendment flow </deferred_reading>

Parse:

-y flag                          → auto_confirm = true
--amend / -a                     → amend_mode = true (running session 存在时触发目标修改流程)
.md/.txt path                    → input_doc (supplementary context only, NEVER substitutes lifecycle stages)
status|continue + session-id     → 当 intent ∈ {status,continue} 且后续 token 匹配 ralph-*|maestro-* → target_session_id
Remaining                        → intent (amend_mode 时为 change_request)

State files:

  • .workflow/state.json — artifact registry, milestones, phases
  • .workflow/roadmap.md — milestone/phase structure
  • .workflow/.maestro/ralph-*/status.json — ralph session state

<state_machine>

S_PARSE_ROUTE: → S_STATUS WHEN: intent == "status" → S_CONTINUE WHEN: intent == "continue" → S_AMEND_GOAL WHEN: amend_mode == true AND running session exists → S_FALLBACK WHEN: amend_mode == true AND no running session DO: Display: "No running session, --amend requires an active session" → S_DECISION_EVAL WHEN: running session with decision step in "running" status → S_PREPARE_SESSION WHEN: intent is non-empty ← derive all facts such as phase/position in one pass → S_FALLBACK WHEN: no intent AND no running session

S_STATUS: → END DO: A_SHOW_STATUS

S_CONTINUE: → S_DISPATCH WHEN: target_session_id provided AND session exists → S_DISPATCH WHEN: running session found (no target_session_id → latest running) → S_FALLBACK WHEN: no running session DO: display "No running ralph session"

S_PREPARE_SESSION: → S_DECOMPOSE WHEN: preparation succeeded DO: A_PREPARE_SESSION → S_FALLBACK WHEN: ambiguous GUARD: auto_confirm does NOT skip phase ambiguity

S_DECOMPOSE: → S_BUILD_CHAIN DO: A_DECOMPOSE_TASKS GUARD: broad intent → MUST clarify boundary even if auto_confirm GUARD: narrow intent → auto-derive, skip questions GUARD: lifecycle_position ∈ {grill, brainstorm, blueprint, init} → skip decomposition

S_BUILD_CHAIN: → S_CREATE_SESSION DO: A_BUILD_STEPS

S_CREATE_SESSION: → S_CONFIRM WHEN: not auto_confirm DO: A_CREATE_SESSION → S_DISPATCH WHEN: auto_confirm DO: A_CREATE_SESSION

S_CONFIRM: → S_DISPATCH WHEN: user selects "Proceed" → S_BUILD_CHAIN WHEN: user selects "Edit" → END WHEN: user selects "Cancel"

S_DISPATCH: → END DO: Skill(maestro-ralph-execute)

S_DECISION_EVAL: (decision node == step.decision is non-empty; the following gate names are taken from that field) → S_APPLY_VERDICT WHEN: quality-gate (post-execute, post-business-test, post-review, post-test) DO: A_DELEGATE_EVALUATE → S_APPLY_VERDICT WHEN: goal-gate (post-goal-audit) DO: A_GOAL_AUDIT_EVALUATE → S_APPLY_VERDICT WHEN: scope-gate (post-analyze-scope) DO: A_SCOPE_EVALUATE → S_APPLY_VERDICT WHEN: reground-gate (post-reground) DO: A_REGROUND_EVALUATE → S_APPLY_VERDICT WHEN: structural (post-milestone, post-debug-escalate) DO: A_STRUCTURAL_EVALUATE

S_APPLY_VERDICT: → S_DISPATCH WHEN: verdict == "proceed" DO: A_APPLY_PROCEED → S_DISPATCH WHEN: post-goal-audit + unmet sub-goals DO: A_APPLY_GOAL_FIX → S_DISPATCH WHEN: post-goal-audit + all sub-goals met DO: A_APPLY_GOAL_DONE → S_DISPATCH WHEN: post-analyze-scope DO: A_APPLY_SCOPE_VERDICT → S_DISPATCH WHEN: verdict == "fix" DO: A_APPLY_FIX → S_DISPATCH WHEN: verdict == "escalate" DO: A_APPLY_ESCALATE → S_DISPATCH WHEN: post-milestone + standard + next milestone DO: A_ADVANCE_MILESTONE → END WHEN: post-milestone + standard + no next milestone DO: mark completed → END WHEN: post-milestone + adhoc DO: mark completed (adhoc self-contained) → END WHEN: post-debug-escalate (always STOP) DO: A_PAUSE_ESCALATE → END WHEN: post-reground + drifted + confidence_score >= 60 DO: A_REGROUND_HALT → S_DISPATCH WHEN: post-reground + aligned DO: A_APPLY_PROCEED → S_DISPATCH WHEN: post-reground + drifted + confidence_score < 60 DO: A_APPLY_PROCEED (marked LOW CONFIDENCE) GUARD: post-reground + drifted + confidence_score >= 60 → A_REGROUND_HALT (drift circuit breaker, auto_confirm does not skip) GUARD: retry_count >= max_retries → force escalate GUARD: confidence_score < 60 AND proceed → override to fix GUARD: confidence_score > 95 AND fix AND retry > 0 → suggest proceed GUARD: auto_confirm → skip user prompt, apply adjusted verdict GUARD: not auto_confirm → request_user_input with override options

S_AMEND_GOAL: → S_DISPATCH WHEN: change applied + user confirmed DO: A_AMEND_GOAL → END WHEN: user cancels GUARD: RISK_LEVEL=high → auto_confirm invalid, force user confirmation

S_FALLBACK: → S_PARSE_ROUTE WHEN: user provides input DO: request_user_input → END WHEN: user cancels

A_SHOW_STATUS

  1. If target_session_id is provided → load directly .workflow/.maestro/{target_session_id}/status.json; otherwise take the latest session (by created_at, regardless of status)
  2. Display: Session, Status, Position, Progress, Current step
  3. List steps: [✓] completion_confirmed, [▸] current, [ ] pending, [◆] decision(step.decision is non-empty); execution step appends command_scope(global/project) + command_path
  4. If task_decomposition present (absent → skip):
    Sub-goals  ({done}/{total})    source: {session_dir}/status.json#/task_decomposition
    [x] G1 done_when={done_when}   evidence={evidence}   confirmed={completion_confirmed}
    [ ] G2 done_when={done_when}   evidence={evidence}   confirmed=false ◀ unmet
    

A_PREPARE_SESSION

Parse phase, infer lifecycle_position, read scope_verdict, decide quality_mode, decide planning_mode in one pass.

1. Phase & Milestone Derivation:

  • Match phase\s*(\d+) -> take the corresponding phase number from state.json.
  • intent-derived phrase -> look up state.json.milestones[*].phase_slugs or artifacts[*].path。
  • newly derived phase -> phase_is_new = true.
  • When parsing a numeric phase, reverse-look up the milestone:
    for ms in state.json.milestones:
        if str(phase_number) in ms.phase_slugs: return ms.id
    return state.json.current_milestone
    

2. Lifecycle Position Derivation:

  • Explicit override:grill(interrogation),brainstorm(storm),blueprint(spec),analyze-macro(broad intent).
  • Startup detection: no .workflow/ -> brainstorm (no source code) / init (has source code); no state.json -> init。
  • Phase-sensitive artifact inference:
    • phase_is_new == true -> analyze
    • latest artifact is analyze -> plan
    • latest artifact is plan -> execute
    • latest artifact is execute -> review

3. Scope Verdict Read:

  • Locate the latest type=="analyze" and scope=="macro" artifact, read conclusions.json of scope_verdict (large | medium | small)。

4. Quality Mode Decision:

  • Explicit override --quality; if none, default: exists specs/REQ-*.md and business is clear -> full (includes business-test/test); otherwise -> standard;--quality quick -> quick。

5. Planning Mode Decision:

  • lifecycle_position ∈ {grill, brainstorm, init, roadmap} -> independent。
  • Otherwise, if the milestone contains multiple phases, set unifiedwhen auto_confirm, and ask the user interactively when not auto_confirm.

6. Persist Write:

  • Write phase, phase_is_new, milestone, lifecycle_position, scope_verdict, quality_mode, planning_mode to status.json。

A_DECOMPOSE_TASKS

Runs once before chain build; additive to status.json.

1. Classify intent breadth:

Pattern Breadth Clarify?
refactor/overhaul/rewrite/redo/holistic/migrate · overhaul/migrate/rewrite/revamp broad MUST (ignores auto_confirm)
named single file/function/bug, "fix X", "add Y to Z" narrow skip — auto-derive
otherwise medium clarify unless auto_confirm

2. Clarify boundary (broad/medium) — request_user_input, ≤3 rounds, options pre-filled from intent + a quick Glob/Grep scan of the target module:

Round Question Drives
Scope Which directories/files/layers are in scope? What is explicitly excluded? boundary_contract.in_scope / out_of_scope
Constraints Must be backward compatible? Public API frozen? Behavior/performance budget? Test threshold? boundary_contract.constraints + execution_criteria
Done What observable result counts as "done"? (e.g., all tests green + zero behavior change + X metric) boundary_contract.definition_of_done

narrow → derive defaults from intent + codebase, skip questions.

3. Derive execution_criteria: backward-compat、scope-freeze、test/coverage bar、fix-don't-hide、incremental commit。

4. Derive task_decomposition (sub-goal list — outcome-oriented, NOT lifecycle stages). Each entry:

{ "id": "G1", "goal": "<deliverable>", "boundary": "<in/out note>",
  "done_when": "<objectively checkable condition>",
  "evidence": "verification.json|review.json|uat.md|<test path>",
  "lifecycle": ["analyze","execute","verify"], "status": "pending" }

done_when Must be objectively verifiable and reference an artifact already produced by ralph;lifecycle Fields map to the lifecycle stage that produces the evidence.

5. Persist (additive): boundary_contract, execution_criteria, task_decomposition. Each sub-goal contains status: "pending" + completion_confirmed: false。

6. Register goal via create_goal:

create_goal({
  objective: "Ralph {intent} — converge {N} sub-goals within boundary",
  success_criteria: task_decomposition.map(g => `${g.id}: ${g.done_when}`),
  constraints: [...execution_criteria,
    "通过 Skill(maestro-ralph-execute) 推进 step,禁止绕过直接执行 steps[*].skill",
    "禁止修改 boundary_contract.out_of_scope"]
})

A_BUILD_STEPS

Generate steps from session.lifecycle_position to milestone-complete(session.milestone when present) or the last quality gate (when standalone).

Stage Skill (independent) Skill (unified) Decision after quality_mode
grill maestro-grill "{intent}" (same) — all (auto_confirm → pass through -y, do not skip)
brainstorm maestro-brainstorm "{intent}" --from grill:{grill_id} (if grill ran) / maestro-brainstorm "{intent}" (otherwise) (same) — all
blueprint maestro-blueprint "{intent}" (same) — all
init maestro-init (same) — all
analyze-macro maestro-analyze "{intent}" (same) post-analyze-scope all
roadmap maestro-roadmap --from analyze:{analyze_macro_id} (same) — all
analyze maestro-analyze {milestone} maestro-analyze — all
plan maestro-plan {milestone} (scope=phase) / maestro-plan --from analyze:{analyze_macro_id} (scope=standalone) / maestro-plan --from blueprint:{blueprint_id} (scope=standalone) maestro-plan — all
execute maestro-execute {phase} maestro-execute post-execute all
business-test quality-auto-test {phase} quality-auto-test post-business-test full only
review quality-review {phase} quality-review post-review all (quick: append --tier quick)
test-gen quality-auto-test {phase} quality-auto-test — full / standard if coverage<80%
test quality-test {phase} quality-test post-test full, standard
milestone-audit maestro-milestone-audit (same) — all
goal-audit (decision-only) (same) post-goal-audit all (only if decomposed)
milestone-complete maestro-milestone-complete (same) post-milestone all

All execution stages uniformly go through maestro ralph next CLI loading + inline execution; decision nodes are inserted separately as independent steps (see rule 4).

Build rules (apply in order):

  1. planning_mode column selection:unified → Skill (unified) column;independent → Skill (independent) column
  2. Starting point: start from session.lifecycle_position start
  3. Skip completed: skip stages that already have a completed artifact under the current milestone+phase (filter by session.phase ); unified filters by milestone
  4. quality_mode filtering: exclude non-matching stages by session.quality_mode 3.5. grill auto_confirm pass-through:auto_confirm == true when it is grill append to step args -y(grill's own Auto mode uses code to answer on its behalf); preserve grill stage and brainstorm's --from grill:*
  5. decision node: after each stage whose Decision is non-empty, insert { decision: "<gate>", retry_count: 0, max_retries: 2, command_scope: null, command_path: null }
  6. goal-audit insertion:task_decomposition when present, after the last evidence-producing stage (verify/review/test), beforemilestone-complete insert decision:post-goal-audit 5.5. re-grounding insertion:WHEN task_decomposition when present AND execution steps (excluding decision) ≥3
    • Starting from the 3rd execution step, insert every 3 steps { decision: "post-reground", retry_count: 0, max_retries: 0, command_scope: null, command_path: null }
    • do not insert after the last execution step (covered by goal-audit)
    • not adjacent to an existing quality-gate decision node (defer to the next 3-step boundary)
    • steps dynamically inserted by fix-loop included incount (recalculate the 3-step interval from the insertion point)
  7. endpoint hard constraint:session.milestone when present, the chain ends with milestone-complete ends with;session.milestone=null(standalone) skip milestone-audit + milestone-complete stage, the chain ends with the last quality-gate stage
  8. goal_ref propagation:task_decomposition when present, each step matches by step.stage ∈ g.lifecycle match step.goal_ref = g.id(multiple matches take the lexicographically smallest); decision nodes do not carry goal_ref
  9. placeholder: independent preserves {phase} {intent}; unified does not carry {phase}
  10. command_path resolution(each execution step, decision nodes skipped):
    • take the skill name (the first token before args)
    • pre-validation passes Bash("maestro ralph skills --platform codex --json --quiet") fetch all available codex skills at once (global ~/.codex/skills/ + project .codex/skills/, project overrides global), match the skill name to get:
      • hit → command_scope = "global" | "project",command_path = <绝对 SKILL.md 路径>
      • Miss → command_scope = "missing", command_path = null, A_CREATE_SESSION reports error E006
    • Do not read SKILL.md content during the build phase;<required_reading> / <deferred_reading> Parsing and loading are performed by maestro ralph next CLI at execution time
  11. Initialize each step completion_confirmed: false, completion_status: null, completion_evidence: null, completion_summary: null, completion_decisions: null, completion_caveats: null, completion_deferred: null, deferred_reads: [], load: null(written by ralph next )
  12. scope_verdict gating(only when the chain start point = analyze-macro):
    • scope_verdict ∈ {medium, small} → skip roadmap + analyze two stages;plan select the standalone column (--from analyze:{analyze_macro_id}), without {phase}
    • scope_verdict == large → retain roadmap + analyze;plan select the phase column ({phase})
    • scope_verdict == unknown → default to the large path; corrected by the post-analyze-scope decision node after macro analyze completes (A_APPLY_SCOPE_VERDICT)
  13. --from auto-injected:
    • analyze_macro_id exists and the current step is roadmap → args changed to --from analyze:{analyze_macro_id}
    • analyze_macro_id exists and scope_verdict ∈ {medium, small} and the current step is plan → args changed to --from analyze:{analyze_macro_id}
    • blueprint_id exists → the current step is plan → args changed to --from blueprint:{blueprint_id}(lower priority than the phase numeric parameter)
    • deferred chaining(standalone mode): the preceding artifact of the build phase has not yet been produced; A_RESOLVE_ARGS (ralph-execute) looks it up from state.json at runtime and injects it:
      • plan step (including the {milestone} placeholder) → look up the latest completed analyze artifact of the same milestone,--from analyze:{milestone_analyze_id}, write source_artifact_ref
      • execute step (including the {phase} placeholder) → look up the latest completed plan artifact of the same phase+milestone,--dir {plan_path}(existing logic), write source_artifact_ref = "plan:{id}"
    • write step.source_artifact_ref for auditing
  14. D-007 Milestone-ref annotation: every step containing the {phase} placeholder → step.milestone_id = session.milestone(derived by reverse lookup via A_RESOLVE_PHASE); reading current_milestone
  15. is prohibited; dynamically insert steps(A_APPLY_*) likewise applies rules 7-13

A_CREATE_SESSION

  1. Validate: all steps' command_scope != "missing"; otherwise raise E006 + list the missing skills
  2. Write .workflow/.maestro/ralph-{YYYYMMDD-HHmmss}/status.json (Appendix: Session Schema); including platform: "codex", cli_tool: "codex"
  3. Display chain overview: each step displays {index}. {skill} [{type}] [{command_scope}]
  4. If task_decomposition present: call create_goal(already registered by A_DECOMPOSE_TASKS) + update_plan, continue handoff

A_DELEGATE_EVALUATE

  1. Resolve artifact dir: .workflow/scratch/{artifact.path}/ with fallback glob
  2. Parse decision metadata: { decision, retry_count, max_retries }
  3. Map result files:
    Decision Files
    post-execute verification.json
    post-business-test .tests/auto-test/report.json
    post-review review.json
    post-test uat.md, .tests/test-results.json
  4. Check artifact for confidence section → include as signal
  5. Execute delegate (run_in_background, STOP, wait for callback):
    maestro delegate "PURPOSE: 评估 {decision} 质量门结果
    TASK: 读取结果 | 分析状态 | 评估严重性 | 给出建议
    EXPECTED: ---VERDICT--- STATUS/REASON/GAP_SUMMARY/CONFIDENCE(high|medium|low)/CONFIDENCE_SCORE(0-100)/WEAKEST_DIMENSION ---END---
    CONSTRAINTS: 只评估 | 置信度<60% 倾向 fix | retry {n}/{max} 达上限必须 escalate"
    --role analyze --mode analysis
    
  6. On callback: parse verdict; if parse fails → fallback STATUS="fix"
  7. Confidence adjustment: <60 + proceed → fix; >95 + fix + retry>0 → suggest proceed
  8. Decision log: Append to {session_dir}/decisions.ndjson:
    { "id": "DEC-{timestamp}", "timestamp": "{ISO}", "source": "ralph",
      "node_id": "{step.decision}", "type": "quality-gate",
      "verdict": "{adjusted_verdict}", "confidence_score": {N},
      "close_call": {N>=50 && N<=70}, "summary": "{REASON}" }
    

A_STRUCTURAL_EVALUATE

post-milestone:

  1. Read state.json → resolve completed milestone object
  2. Determine milestone type: milestone_obj.type (default "standard" if missing)
  3. Standard milestone (type != "adhoc"): next milestone exists? → insert lifecycle steps / complete
  4. Adhoc milestone (type == "adhoc"): always END — adhoc milestones are self-contained, no successor to advance to. Set current_milestone = null.

post-debug-escalate: Always STOP → set paused, display "please intervene manually"

A_SCOPE_EVALUATE

Triggered only by the post-analyze-scope decision node; after macro analyze completes, read conclusions.json.scope_verdict to determine the downstream chain.

  1. Locate the just-completed macro analyze artifact → analyze_macro_id, conclusions_path = {artifact_path}/conclusions.json
  2. read conclusions.scope_verdict(large | medium | small), missing → unknown
  3. write session.scope_verdict + session.analyze_macro_id
  4. Append {session_dir}/decisions.ndjson:
    { "id": "DEC-{timestamp}", "type": "scope-gate",
      "source": "ralph", "node_id": "post-analyze-scope",
      "verdict": "{scope_verdict}", "analyze_macro_id": "{ANL_ID}" }
    
  5. → A_APPLY_SCOPE_VERDICT

A_GOAL_AUDIT_EVALUATE

Runs only when task_decomposition present.

  1. Read session.task_decomposition from status.json
  2. For each sub-goal status != "done": resolve evidence artifact under current phase scratch dir
  3. Delegate read-only audit (run_in_background, STOP, wait):
    maestro delegate "PURPOSE: 审计未完成子目标,判定 met / unmet
    TASK:
      1. 读取 status.json.task_decomposition 中 status!=done 的子目标
      2. 打开 evidence 产物,对照 done_when 严格判定
      3. 输出 met / unmet,unmet 给出 gap + target_phase
    CONTEXT:
      status.json   = {session_dir}/status.json
      evidence      = {evidence artifacts}
      execution_criteria = {execution_criteria}
      boundary_contract  = {boundary_contract}
    EXPECTED:
      ---VERDICT---
      STATUS=all_met|has_unmet
      UNMET=[{id:G2,gap:'...',target_phase:execute}, ...]
      CONFIDENCE_SCORE=0-100
      ---END---
    CONSTRAINTS:
      - 只评估,不修改文件
      - 严格按 done_when 判定;evidence 缺失 → unmet
      - 不得建议超出 boundary_contract 的修改
    "
    --role analyze --mode analysis
    
  4. On callback: for each met sub-goal, set task_decomposition[i].status="done" + completion_confirmed=true + completed_at=now
  5. Append {session_dir}/decisions.ndjson with "type": "goal-gate", unmet_count, unmet_ids
  6. Verdict: all_met → A_APPLY_GOAL_DONE; has_unmet → A_APPLY_GOAL_FIX GUARD: retry_count >= max_retries AND still unmet → A_APPLY_ESCALATE

A_APPLY_PROCEED

  1. Mark decision completed, write status.json
  2. Display: ◆ Decision: {type} → proceed ({reason})

A_APPLY_FIX

  1. Insert fix-loop commands after current step (see Appendix: Fix-Loop Templates)
  2. Reindex steps, increment retry_count, write status.json
  3. Display: ◆ Decision: {type} → fix, +{N} commands inserted

A_APPLY_ESCALATE

  1. Insert [quality-debug "{gap_summary}", decision:post-debug-escalate]
  2. Increment retry_count, reindex, write status.json

A_APPLY_SCOPE_VERDICT

Triggered by post-analyze-scope , based on session.scope_verdict reshape the downstream chain.

  1. read session.scope_verdict
  2. Path A (large): keep the current chain; for subsequent roadmap step inject --from analyze:{analyze_macro_id}; for subsequent plan step select the phase column; continue advancing
  3. Path B (medium / small):
    • delete all incomplete goal-audit before roadmap + analyze (phase) step
    • change the next incomplete plan step to maestro-plan --from analyze:{analyze_macro_id}, remove {phase},source_artifact_ref = analyze:{analyze_macro_id}
    • Subsequent execute / verify etc. continue with the same standalone scope (without {phase}, driven by the task list written by plan)
  4. Path C (unknown):
    • not auto_confirm → request_user_input choose one of two (large / medium-small); auto_confirm → default large
  5. Reindex steps, mark decision completed, write status.json
  6. Display: ◆ Scope verdict: {verdict} → {kept|collapsed to standalone via analyze:{ANL_ID}}

A_APPLY_GOAL_FIX

  1. For each unmet subgoal G{n}(deduplicated by target_phase grouping): before the goal-audit node, insert a scoped mini-loop (see Appendix: Fix-Loop Templates → post-goal-audit), and for each inserted step goal_ref: "G{n}", parse according to A_BUILD_STEPS rule 9 command_path
  2. re-append decision:post-goal-audit {retry+1}
  3. Reindex steps, increment retry_count, write status.json
  4. Display: ◆ Goal audit: {k} unmet → +{N} steps inserted (G{ids}), retry {r}/{max}

A_APPLY_GOAL_DONE

  1. status.json: set each task_decomposition[*].status="done", completion_confirmed=true, completed_at=now, top-level task_decomposition_all_done=true
  2. Mark goal-audit decision completed;proceed to milestone-complete
  3. Display: ◆ Goal audit: all met ✓

A_ADVANCE_MILESTONE

  1. Update session: milestone, phase, reset passed_gates
  2. Insert full lifecycle steps for next milestone
  3. Reindex, write status.json

A_REGROUND_EVALUATE

GUARD: task_decomposition exists (periodically triggered, see build rule 5.5)

  1. Read status.json:
    • session.intent, session.boundary_contract
    • steps[] WHERE status=="completed" → take completion_evidence, completion_summary, completion_decisions, completion_caveats
    • task_decomposition[] WHERE status=="done" → take goal, done_when
  2. Delegate read-only audit (run_in_background, STOP, wait):
    maestro delegate "PURPOSE: 意图保真检查 — 对照 intent 验证累积执行是否漂移
    TASK:
      1. 读取 intent + boundary_contract.definition_of_done
      2. 读取已完成 steps 的 completion_summary + completion_decisions
      3. 判定累积产出是否仍服务 intent;是否有 step 产出超出 in_scope 或触碰 out_of_scope
      4. 输出 aligned / drifted
    CONTEXT:
      intent             = {session.intent}
      definition_of_done = {boundary_contract.definition_of_done}
      in_scope           = {boundary_contract.in_scope}
      out_of_scope       = {boundary_contract.out_of_scope}
      completed_steps    = [{index, skill, stage, completion_evidence, completion_summary, completion_decisions, completion_caveats}, ...]
      done_goals         = [{id, goal, done_when}, ...]
      accumulated_deferred = [{from_step, item}, ...]
      goal_changelog     = {session.goal_changelog ?? []}
    EXPECTED:
      ---VERDICT---
      STATUS=aligned|drifted
      DRIFT_DESCRIPTION=<空或具体描述>
      CORRECTIVE_ACTION=<空或建议>
      CONFIDENCE_SCORE=0-100
      ---END---
    CONSTRAINTS:
      - 只评估不修改
      - aligned 阈值:≥80% 已完成产出直接服务 intent
      - 单个 step 触碰 out_of_scope → 直接判 drifted
      - goal_changelog 存在 → 以最新 after.goals 为基准"
    --role analyze --mode analysis
    
  3. On callback: parse verdict
  4. Append {session_dir}/decisions.ndjson:{ "id": "DEC-{ts}", "type": "reground-gate", "source": "ralph", "node_id": "post-reground", "verdict": "{aligned|drifted}", "confidence_score": {N} }
  5. Verdict routing:aligned → A_APPLY_PROCEED;drifted + confidence_score >= 60 → A_REGROUND_HALT;drifted + confidence_score < 60 → A_APPLY_PROCEED (mark LOW CONFIDENCE)

A_REGROUND_HALT

Drift circuit breaker (safety gate, auto_confirm does not skip).

  1. Set session.status = "paused",write status.json
  2. Display:
    ⚠️ Re-grounding 检测失败 — 执行已偏离 intent。
    Intent: {session.intent}
    Drift:  {drift_description}
    建议回归: {corrective_action}
    选项:1) Skill(maestro-ralph, "continue") 忽略漂移继续  2) 手动修正后 continue  3) Skill(maestro-ralph, "status") 查看后决定
    
  3. GUARD: auto_confirm is ineffective for this action—the drift circuit breaker cannot be automatically skipped

A_PAUSE_ESCALATE

  1. Set session status = "paused", write status.json
  2. Display: ◆ Maximum retry count reached, debug has been executed. Manual intervention required.
  3. Display: Skill(maestro-ralph, "continue") resume

A_AMEND_GOAL

Modify the goal of a running session. The detailed procedure is loaded by <deferred_reading> loads ralph-amend-goal.md。

Phase behavior output
1. Snapshot Read task_decomposition + boundary_contract + the completed steps' completion_summary Display: goal list + progress
2. Parse change_request non-empty → use directly; empty → request_user_input (modify/add/remove/adjust boundaries) change_type + change_request
3. Mini Grill maestro delegate --role analyze --mode analysis: assess impact RISK_LEVEL + AFFECTED_GOALS + INVALIDATED_STEPS + NEW_GAPS
4. Confirm request_user_input: apply and continue / only change the goal / cancel User selection
5. Apply Archive the old goal (superseded) → write the new goal (origin: CHG-xxx) → rebuild the chain → write status.json handoff Skill(maestro-ralph-execute)

GUARD: RISK_LEVEL == high → request_user_input is not skipped (auto_confirm is ineffective) GUARD: a completed (status: "done") goal cannot be superseded (skip + warn)

</state_machine>

Session Schema

{
  "session_id": "ralph-{YYYYMMDD-HHmmss}",
  "source": "ralph", "status": "running",
  "ralph_protocol_version": "2",   // CLI-driven; absent/0 → legacy; "1" → basic CLI; "2" → structured completion + enhanced anchor
  "active_step_index": null,       // CLI-managed; only one step held at a time
  "intent": "", "lifecycle_position": "",
  "phase": null, "phase_is_new": false,
  "milestone": "",                // D-007 反查结果,禁止读 current_milestone
  "auto_mode": false,
  "quality_mode": "standard",     // "full" | "standard" | "quick"
  "planning_mode": "independent", // "unified" | "independent"
  "scope_verdict": null,          // "large" | "medium" | "small" | "unknown" | null
  "analyze_macro_id": null,       // "ANL-xxx" 来自最新 macro analyze
  "blueprint_id": null,           // "BLP-xxx" 若存在
  "cli_tool": "codex",
  "platform": "codex",            // codex skills (`.codex/skills/`)
  "passed_gates": [],
  "context": { "issue_id": null, "scratch_dir": null, "plan_dir": null,
    "analysis_dir": null, "brainstorm_dir": null, "blueprint_dir": null },
  "steps": [{
    "index": 0,
    "skill": "",                  // 执行 step 有值;decision 节点为空字符串/null
    "args": "",
    "stage": "",                  // brainstorm|blueprint|init|analyze-macro|roadmap|analyze|plan|execute|...
    "scope": null,                // "phase"|"standalone"|"milestone"|null(plan 等需要)
    "decision": null,             // 非 null → decision 节点(值为 gate 名,如 "post-execute");null → 执行 step
    "retry_count": 0,             // decision 节点专用
    "max_retries": 2,             // decision 节点专用
    "command_scope": "global|project|missing|null",  // 执行 step;decision 节点固定 null
    "command_path": "<absolute SKILL.md path resolved by `maestro ralph skills --platform codex --json --quiet`> | null",
    "milestone_id": null,         // D-007 反查注入;仅含 {phase} 占位符的 step 有
    "source_artifact_ref": null,  // "analyze:ANL-xxx" | "blueprint:BLP-xxx" | null
    "status": "pending|running|completed|skipped|failed",
    "goal_ref": null,
    "completion_confirmed": false,
    "completion_status": null,
    "completion_evidence": null,
    "completion_summary": null,      // 一句话总结:做了什么(MUST on DONE)
    "completion_decisions": null,    // 本 step 做出的关键决策列表
    "completion_caveats": null,      // 后续 step 需注意的事项
    "completion_deferred": null,     // 被推迟到后续的工作列表
    "completed_at": null,
    "deferred_reads": [],         // 由 ralph next CLI 解析 SKILL.md 时填充
    "load": null                  // { loaded_at, required_files[], deferred_files[], resolve_version } —— 由 ralph next 写入
  }],
  "waves": [], "current_step": 0,

  // Optional decomposition block (additive; absent → decomposition off)
  "boundary_contract": {
    "in_scope": [], "out_of_scope": [], "constraints": [], "definition_of_done": ""
  },
  "execution_criteria": [],
  "task_decomposition": [
    { "id": "G1", "goal": "", "boundary": "", "done_when": "",
      "evidence": "", "lifecycle": [], "status": "pending|done|superseded",
      "completion_confirmed": false, "completed_at": null,
      "superseded_by": null, "superseded_at": null, "origin": null }
  ],
  "task_decomposition_all_done": false,

  // goal_changelog: additive; absent → no amendments
  "goal_changelog": [
    { "id": "CHG-001", "timestamp": "{ISO}",
      "change_type": "modify|add|remove|boundary",
      "reason": "变更描述",
      "impact_assessment": { "risk_level": "low|medium|high",
        "invalidated_steps": [], "new_steps_inserted": 0 },
      "before": { "goals": [{"id":"G1","goal":"...","done_when":"..."}] },
      "after":  { "goals": [{"id":"G1v2","goal":"...","done_when":"..."}] } }
  ]
}

New fields are optional; default = old behavior; existing field names are neither deleted nor changed.

Fix-Loop Templates

All inserted execution steps parse according to A_BUILD_STEPS rule 9 command_path + command_scope;decision:* entries as decision nodes (step.decision field).

post-execute:

quality-debug "{gap_summary}"
maestro-plan --gaps {phase}
maestro-execute {phase}
decision:post-execute {retry+1}

post-business-test:

quality-debug --from-business-test "{gap_summary}"
maestro-plan --gaps {phase}
maestro-execute {phase}
decision:post-execute {retry: 0}
quality-auto-test {phase}
decision:post-business-test {retry+1}

post-review:

quality-debug "{gap_summary}"
maestro-plan --gaps {phase}
maestro-execute {phase}
quality-review {phase}
decision:post-review {retry+1}

post-test:

quality-debug --from-uat "{gap_summary}"
maestro-plan --gaps {phase}
maestro-execute {phase}
decision:post-execute {retry: 0}
quality-auto-test {phase}
decision:post-business-test {retry: 0}
quality-review {phase}
decision:post-review {retry: 0}
quality-auto-test {phase}
quality-test {phase}
decision:post-test {retry+1}

post-goal-audit: (per unmet sub-goal group)

# for each unmet sub-goal G{n}, scoped to target_phase:
maestro-plan --gaps {target_phase} "G{n}: {gap}"     [goal_ref: G{n}]
maestro-execute {target_phase}                       [goal_ref: G{n}]
# after all unmet groups inserted:
decision:post-goal-audit {retry+1}

Goal Management (Codex Built-in)

After Decomposition output, manage goals through Codex built-in tools (called by A_DECOMPOSE_TASKS step 6):

  • create_goal — register goal + success_criteria + constraints
  • update_plan — sync steps[] progress to the Codex plan view
  • update_goal — release on convergence (A_APPLY_GOAL_DONE / session completed); keep on abort/pause (supports Skill(maestro-ralph, "continue") resume)

Error Codes

Code Severity Description Recovery
E001 error No intent and no running session Prompt for intent
E002 error Cannot infer lifecycle position Show raw state, ask
E003 error Artifact dir not found for decision Show glob, ask
E004 error Delegate verdict parse failed Fallback: "fix"
E005 error Delegate execution failed Fallback: "fix"
E006 error command_scope == "missing" for one or more steps List missing skills, abort build
W001 warning Decision expanded chain Auto-handled
W002 warning Max retries, escalating Auto-handled
W003 warning Multiple running sessions Use latest, warn
W004 warning Low delegate confidence Show warning

Success Criteria

  • Phase is resolved before position; the phase_is_new flag is written to session
  • D-007 reverse lookup: phase number → session.milestone, reading current_milestone is prohibited; write to step.milestone_id
  • phase_is_new=true → lifecycle_position forced analyze
  • Intent overrides identify grill / brainstorm / blueprint / analyze-macro
  • when auto_confirm=true, append to grill step args -y(Auto mode code auto-answer, stage not skipped)
  • A_RESOLVE_SCOPE_VERDICT reads macro analyze conclusions.scope_verdict, writes to session.scope_verdict + analyze_macro_id
  • Chain start point = at analyze-macro: large→roadmap+analyze+plan(milestone); medium/small→jump directly to plan --from analyze:{ANL_ID} (skip roadmap+analyze)
  • post-analyze-scope decision node is inserted after macro analyze; A_SCOPE_EVALUATE/A_APPLY_SCOPE_VERDICT reshape the chain
  • plan step args support three paths:{milestone} / --from analyze:{ANL_ID} / --from blueprint:{BLP_ID}, write to step.source_artifact_ref
  • roadmap step args automatically inject --from analyze:{analyze_macro_id}(if present)
  • artifact filtering by session.phase; unified by milestone
  • quality_mode is determined by A_DETERMINE_QUALITY_MODE, filters build steps
  • Decomposition: broad intent ≤3 question clarify;narrow auto-derive
  • status.json single source of truth: boundary_contract + execution_criteria + task_decomposition; no external manifest
  • execution step contains command_scope + command_path(pre-validated via maestro ralph skills --platform codex --json --quiet pre-validation, project overrides global); decision step identified via step.decision field
  • Ralph build phase only validates path existence via ralph skills --platform codex , does not read SKILL.md content;<required_reading> loading is done by maestro ralph next CLI
  • each step contains completion_confirmed + completion_status + completion_evidence + deferred_reads(initially false/null/[])
  • each sub-goal contains completion_confirmed(initially false)
  • post-goal-audit decision is inserted only when decomposed, located before milestone-complete
  • Unmet sub-goals dynamically grow steps[] (goal_ref tagged); max retries → escalate
  • planning_mode explicitly determined; unified=no placeholders, independent=analyze/plan with {milestone}, execute/quality with {phase}
  • Chain must end with milestone-complete end
  • Decision nodes are evaluated by maestro delegate --role analyze
  • Ralph does not execute steps, only evaluates;Skill(maestro-ralph-execute) directly calls handoff
  • session.platform = "codex"; all CLI calls carry --platform codex
  • Deferred chaining: plan/execute step's --from/--dir injection is done at runtime by A_RESOLVE_ARGS (ralph-execute); build phase marks intent, does not know artifact ID in advance
  • Milestone-level plan step obtains at runtime --from analyze:{milestone_analyze_id}(looked up and injected from state.json by ralph-execute)
  • Phase-level execute step obtains at runtime source_artifact_ref = "plan:{id}"
  • each step contains completion_summary + completion_decisions + completion_caveats + completion_deferred(initially null)
  • completion_summary is MUST at DONE/DONE_WITH_CONCERNS (passed in via CLI --summary parameter)
  • session_anchor contains the completion_summary + completion_caveatsof the most recent 5 completed steps (sliding window)
  • session_anchor contains the task_decomposition global view (only status != "superseded" goals)
  • session_anchor contains Accumulated Signals (aggregates all caveats + deferred)
  • --amend routes to S_AMEND_GOAL (requires running session)
  • A_AMEND_GOAL executes 5 phases (snapshot→parse→mini grill→confirm→apply), each phase produces auditable
  • old goal marked superseded(superseded_by + superseded_at), new goal marked origin: "CHG-xxx"
  • goal_changelog records complete before/after snapshot + impact_assessment
  • RISK_LEVEL=high amend does not skip auto_confirm when
  • re-grounding completes, steps information includes completion_summary/decisions/caveats
  • fix-loop dynamically inserted steps are counted in the re-grounding 3-step count
  • post-reground + drifted + confidence >= 60 → A_REGROUND_HALT (auto_confirm is not skipped)
  • session_anchor boundary_contract is not truncated (capAnchorList n=8)