orca-graph

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Skill: orca-graph

Skill: orca-graph

Nhánh của
orca-workflow
: cùng propose → gate → plan → dispatch, nhưng deps là DỮ LIỆU (graph.json), không phải suy đoán trong đầu. Runtime:
harness/scripts/orca-graph.py
. Vẽ:
fdk/tools/graph-viz.py
(1 graph) +
fdk/tools/graph-atlas.py
(atlas 2D). Store mặc định
llmwiki/graph/
.
Engine sống ở repo riêng
https://github.com/Rheinmir/orca-graph
(test + bộ eval VT + lịch sử riêng), cài vào
~/.orca-graph/repo/
. Ba đường dẫn ở trên trong overstack là shim trỏ sang engine đó — lệnh gõ y như cũ. Shim báo "chưa cài engine" (rc 3) → chạy đúng lệnh nó in ra:
curl -fsSL https://raw.githubusercontent.com/Rheinmir/orca-graph/main/install.sh | bash
. Không có overstack: gọi thẳng
~/.orca-graph/bin/orca-graph
.
orca-workflow
的一个分支:同样采用 propose → gate → plan → dispatch,但
deps
是数据(
graph.json
),而不是脑内推测。Runtime:
harness/scripts/orca-graph.py
。绘图:
fdk/tools/graph-viz.py
(1 个 graph)+
fdk/tools/graph-atlas.py
(2D atlas)。默认 store 为
llmwiki/graph/
。
Engine 位于独立 repo
https://github.com/Rheinmir/orca-graph
(包含测试、独立 VT eval 套件及独立历史),安装到
~/.orca-graph/repo/
。上述位于 overstack 的三个路径都是指向该 engine 的 shim——命令用法与以前相同。Shim 报告“尚未安装 engine”(rc 3)→ 运行它打印出的确切命令:
curl -fsSL https://raw.githubusercontent.com/Rheinmir/orca-graph/main/install.sh | bash
。没有 overstack 时:直接调用
~/.orca-graph/bin/orca-graph
。

WHAT

WHAT

Purpose và context

目的与上下文

  • Purpose: phân việc của một PLAN.md thành ĐỒ THỊ PHỤ THUỘC (deps là DỮ LIỆU trong graph.json), trả lời 5 câu hỏi bằng tool tất định, dispatch theo lớp topo có khoá + lease + generation, state bền append-only, và chấm mọi câu trả lời của model theo rubric có nguồn.
  • Trigger (when to use):
    • Có PLAN.md ≥ 3 task và cần biết: cái gì chạy song song, cái gì chờ cái gì, chạy tới đâu rồi.
    • Dispatch nhiều agent và cần khoá để 2 agent không giành cùng task / ghi cùng file.
    • Việc còn dở nhiều phiên: state phải sống qua crash, không được "nhớ trong đầu".
  • Non-goals: KHÔNG dùng cho sự cố (→
    orca-issue
    ), không dùng khi chưa có PLAN (→
    /propose
    rồi
    /plan
    ). Ngoài phạm vi PRD v1.1 (nói thẳng): item pipeline bền có outbox/backpressure, layered fan-in theo token, anchor registry, routing model theo eval floor, scale proposal, seen ledger cho discovery — xem
    evals/vt-matrix.json
    của repo engine: 13/28 kịch bản VT ghi
    out_of_scope
    kèm lý do. Ngoài phạm vi PRD (nói thẳng, không giả vờ có): PostgreSQL ledger, secret gateway, ngân sách tiền, LangGraph, integration queue/candidate hash, compensation cho effect ngoài, sandbox process-level (chạy lệnh agent trong container/VM riêng). Tool này là file-based cho một máy; cần những thứ trên thì đó là engine khác, không phải nâng cấp orca-graph. (Allow-list GHI file — khác sandbox process — đã có, xem
    run --strict
    ở mục Reference — Daemon & control-room bên dưới và GH#162.)
  • 目的: 将一个 PLAN.md 中的工作拆分为依赖图(deps 是
    graph.json
    中的数据),使用确定性工具回答 5 个问题,按带锁、lease 和 generation 的拓扑层进行调度,维护持久化 append-only 状态,并依据带来源的 rubric 评判模型的每个回答。
  • Trigger(何时使用):
    • PLAN.md 中有 ≥ 3 个 task,且需要知道:哪些任务可以并行运行、哪些任务必须等待其他任务、目前执行到哪里。
    • 需要 dispatch 多个 agent,并需要锁来防止两个 agent 争抢同一 task 或同时写入同一文件。
    • 跨多个 session 仍有未完成工作:state 必须能在 crash 后继续存在,不能只“记在脑中”。
  • Non-goals: 不用于故障处理(→
    orca-issue
    );没有 PLAN 时不适用(→
    /propose
    ,然后
    /plan
    )。 明确说明 PRD v1.1 范围之外的功能:带 outbox/backpressure 的持久化 item pipeline、按 token 分层的 fan-in、anchor registry、依据 eval floor 的模型路由、scale proposal、用于 discovery 的 seen ledger——参见 engine repo 中的
    evals/vt-matrix.json
    :28 个 VT 场景中有 13 个被记录为
    out_of_scope
    ,并附有原因。 明确说明超出 PRD 范围、不能假装已经具备的功能:PostgreSQL ledger、secret gateway、金额预算、LangGraph、integration queue/candidate hash、外部 effect 的 compensation、process-level sandbox(在独立 container/VM 中运行 agent 命令)。此工具是面向单机的 file-based 实现;如果需要上述能力,应使用另一个 engine,而不是将 orca-graph 升级成那样。(GHI 文件 allow-list——不同于 process-level sandbox——已经存在;参见下方 Reference — Daemon & control-room 中的
    run --strict
    以及 GH#162。)

Mental model

心智模型

PLAN.md → build → graph.json (cache) + events.jsonl (nguồn chân lý, append-only) → ask (5 câu hỏi) → next/lock/set/run theo lớp topo → verify (+ qc) → audit → graph-viz / graph-atlas / control-room
.
Máy state mỗi node:
proposed → ready (mọi deps xong) → locked → dispatched → done | done_unverified | failed | unknown
;
blocked
= HITL chờ người. Ba chiều tách nhau:
state
(vòng đời) ·
verified
(verify rc 0?) ·
fresh
(upstream làm lại sau khi mình xong →
stale
, chỉ cảnh báo). Luật vay từ Reprise PRD: op_key idempotent · CAS
--if-rev
· generation chặn kết quả cũ · lease hết →
unknown
không phải
failed
· không verify thì không
done
.
  • qc
    (GH#163, tuỳ chọn — trường
    **QC:**
    trong PLAN.md, nằm trong
    spec_hash
    như
    verify
    ): lệnh review ĐỘC LẬP chạy SAU
    verify
    rc=0, KHÔNG chạy bởi cùng lời gọi đã tự verify (
    by != "reconcile"
    ở
    emit()
    ) — tách vai reviewer khỏi vai người/agent vừa tự verify. Fail thì: qua
    run
    /
    set done
    trực tiếp →
    emit()
    demote
    done
    →
    done_unverified
    (giống verify fail); qua
    reconcile
    → kết luận
    ready
    (reconcile tự quyết dứt khoát, không để lửng done_unverified). Không khai
    **QC:**
    → hành vi y hệt trước đây (tương thích ngược).
PLAN.md → build → graph.json(cache)+ events.jsonl(唯一真实来源,append-only)→ ask(5 个问题)→ 按拓扑层执行 next/lock/set/run → verify(+ qc)→ audit → graph-viz / graph-atlas / control-room
。
每个 node 的 state:
proposed → ready(所有 deps 完成)→ locked → dispatched → done | done_unverified | failed | unknown
;
blocked
表示 HITL,正在等待人员介入。 三个相互独立的维度:
state
(生命周期)·
verified
(verify 是否 rc 0?)·
fresh
(upstream 在自身完成后重新执行 → 标记为
stale
,仅发出警告)。 借鉴 Reprise PRD 的规则:op_key 幂等 · CAS
--if-rev
· generation 阻止旧结果写入 · lease 过期 →
unknown
,而不是
failed
· 未 verify 不得标记为
done
。
  • qc
    (GH#163,可选——PLAN.md 中的
    **QC:**
    字段,且与
    verify
    一样纳入
    spec_hash
    ):独立 review 命令在
    verify
    rc=0 之后运行,不得由刚刚自行 verify 的同一次调用执行(
    emit()
    中要求
    by != "reconcile"
    )——将 reviewer 角色与刚刚自行 verify 的人员/agent 分离。失败时:通过
    run
    /
    set done
    直接完成 →
    emit()
    将
    done
    降级为
    done_unverified
    (与 verify 失败相同);通过
    reconcile
    → 判定为
    ready
    (reconcile 自主作出最终判定,不让节点悬挂在
    done_unverified
    )。未声明
    **QC:**
    时,行为与此前完全一致(向后兼容)。

Input và output contract

输入与输出契约

FieldRequired?Ý nghĩa
In
PLAN.md
có≥ 3 task; dòng
**Depends:**
,
**Verify:**
, tuỳ chọn
**Kind:**
,
**QC:**
,
**Resources:**
; chưa có → gọi skill
plan
Inlý do cạnhnên có
**Depends:** Task 1 (data), Task 2 (preference)
— reason ∈ data · contract · acceptance · effect_order · control (cạnh CỨNG) · preference (chỉ do thứ tự viết)
Inclaim tài nguyênkhi dùng chung
**Resources:** db-migration(exclusive), api-x(shared), llm(capacity:2)
— thiếu mode = exclusive
Instorekhôngmặc định
llmwiki/graph/
In
--parent <gid>/<node>
khônggắn graph con vào node graph mẹ
Inagent + lệnh agentkhi dispatchtên agent cho
lock --by
; lệnh cho
run … --
Out
<id>.graph.json
+
<id>.events.jsonl
+
.locks/
cógraph + state bền
Outoutput
build
cócycle, deps suy luận (
gợi-ý
), xung đột ghi cùng file giữa 2 node song song
Outanswer có nhãn + nguồnkhi model trả lờichấm theo rubric 1 / 0 / 0.3 / 0.5 / bịa 0
OutHTML graph + atlas 2D +
control-room.html
có2 file python vẽ + generator control-room
Out
audit-log.jsonl
khi kếtkết quả mở lại từng nguồn, bịa = 0
FieldRequired?含义
输入
PLAN.md
是≥ 3 个 task;包含
**Depends:**
、
**Verify:**
行,可选
**Kind:**
、
**QC:**
、
**Resources:**
;不存在时 → 调用 skill
plan
输入边的原因建议提供
**Depends:** Task 1 (data), Task 2 (preference)
——reason ∈ data · contract · acceptance · effect_order · control(硬边)· preference(仅因书写顺序)
输入资源 claim存在共享时
**Resources:** db-migration(exclusive), api-x(shared), llm(capacity:2)
——缺少 mode 时默认为 exclusive
输入store否默认
llmwiki/graph/
输入
--parent <gid>/<node>
否将子 graph 挂载到父 graph 的 node 上
输入agent + agent 命令dispatch 时agent 名称用于
lock --by
;命令用于
run … --
输出
<id>.graph.json
+
<id>.events.jsonl
+
.locks/
是graph + 持久化 state
输出
build
输出
是cycle、推断出的 deps(
gợi-ý
)、两个并行 node 的同文件写入冲突
输出带标签和来源的 answermodel 回答时按 rubric 评分:1/0/0.3/0.5/捏造为 0
输出HTML graph + 2D atlas +
control-room.html
是2 个 Python 绘图文件 + control-room generator
输出
audit-log.jsonl
结束时重新打开每个来源进行核对,捏造数 = 0

Rules và capabilities

规则与能力

  • RULE-01 (MUST): Lock kiểm soát DISPATCH; side-effect ghi file có allow-list MỀM (GH#162) — xem
    run --strict
    ở trên. Allow-list KHÔNG thay thế cách ly process thật → worktree riêng mỗi task vẫn là lựa chọn khi cần cô lập hoàn toàn (chạy lệnh, biến môi trường, side-effect ngoài filesystem).
  • RULE-02 (MUST): Không dispatch node
    blocked
    (HITL) cho CLI headless — nó sẽ đoán thay người rồi im lặng (bài học 250626, giao ~1/5).
  • RULE-03 (MUST): Mọi câu trả lời của model về graph phải qua
    answer
    với nhãn + nguồn mở được. Không có nguồn → chọn
    không-biết
    (0.3) thay vì bịa (0).
  • RULE-04 (MUST): Deps
    gợi-ý
    (suy luận) phải được user xác nhận hoặc khai
    **Depends:**
    trước khi dispatch lớp đó.
  • RULE-05 (MUST): Không xoá/sửa tay
    events.jsonl
    ; sai thì append event sửa.
    graph.json
    chỉ là cache — hỏng thì
    build
    lại, state fold từ events.
  • RULE-06 (MUST): HTML sinh ra: toggle sáng/tối + full path + thuật ngữ có giải nghĩa (luật fdk) — 2 file vẽ đã lo, đừng viết HTML tay.
  • RULE-08 (MUST): Tranh chấp tài nguyên KHÔNG phải cạnh DAG (PRD v1.1 §23.2). Hai task độc lập dùng chung nhánh tích hợp / schema DB / cổng test / quota API → khai
    **Resources:**
    , để
    lock
    tuần tự hoá lúc chạy; ĐỪNG thêm
    **Depends:**
    giả. Worktree riêng không miễn claim.
  • RULE-09 (MUST):
    audit-edges
    chỉ ĐỌC và chỉ ĐỀ XUẤT. Cạnh thiếu lý do (
    EDGE_UNJUSTIFIED
    ) thì GIỮ và hỏi user; "không thấy dependency" không bằng "đã chứng minh độc lập". Bỏ cạnh = user đồng ý → sửa PLAN → build lại.
  • RULE-10 (MUST): User yêu cầu THÊM việc vào graph đang chạy →
    add-node
    (nó sửa PLAN gốc rồi build lại,
    plan_version + 1
    , lịch sử giữ nguyên). Cấm vá tay
    graph.json
    ; cấm tạo graph mới cho cùng một goal.
  • RULE-07 (MUST): Không làm được (nói thẳng): coupling ngầm không lộ ra file; rollback tự động khi agent chết nửa chừng; sync 2 chiều với sổ Orca; atlas > ~500 node cần graphviz; allow-list chỉ soát filesystem, không soát network/process/secret access.
  • Capabilities: đọc PLAN và file dự án; ghi store graph append-only + khoá file; spawn và theo dõi process agent (heartbeat theo pid); chạy lệnh verify/qc; đọc diff git để soát allow-list; sinh HTML tĩnh. Mirror một chiều sang sổ điều phối ngoài là tuỳ chọn.
  • RULE-01 (MUST):锁用于控制 DISPATCH;文件写入副作用采用宽松 allow-list(GH#162)——参见上文的
    run --strict
    。Allow-list 不能替代真正的 process 隔离 → 当需要完全隔离时(命令执行、环境变量、filesystem 以外的副作用),每个 task 使用独立 worktree 仍是可选方案。
  • RULE-02 (MUST):不得向 headless CLI dispatch
    blocked
    node
    (HITL)——它会代替人员猜测,然后保持沉默(250626 的经验,约占 1/5)。
  • RULE-03 (MUST):model 对 graph 的所有回答都必须经过
    answer
    ,并附带可打开的标签与来源。没有来源 → 选择
    không-biết
    (0.3),而不是捏造(0)。
  • RULE-04 (MUST):推断得出的
    gợi-ý
    deps 必须在 dispatch 对应层之前得到用户确认,或预先声明
    **Depends:**
    。
  • RULE-05 (MUST):不得删除或手动编辑
    events.jsonl
    ;如需修正,应 append 一个修正事件。
    graph.json
    只是 cache——损坏后重新
    build
    ,并从 events 折叠恢复 state。
  • RULE-06 (MUST):生成的 HTML 必须支持明暗切换、显示完整路径,并为术语提供解释(fdk 规则)——2 个绘图文件已经实现,不要手写 HTML。
  • RULE-08 (MUST):资源争用不是 DAG 边(PRD v1.1 §23.2)。两个独立 task 共享集成分支/DB schema/test gate/API quota → 声明
    **Resources:**
    ,让
    lock
    在执行时将它们串行化;不要添加虚假的
    **Depends:**
    。独立 worktree 不会免除资源 claim。
  • RULE-09 (MUST):
    audit-edges
    只能读取并提出建议。发现缺少原因的边(
    EDGE_UNJUSTIFIED
    )→ 保留该边并询问用户;“没有看到 dependency”不等于“已证明二者独立”。移除边需要用户同意 → 修改 PLAN → 重新 build。
  • RULE-10 (MUST):用户要求向正在运行的 graph 添加工作 →
    add-node
    (它会修改原始 PLAN 并重新 build,
    plan_version + 1
    ,保留历史)。禁止手动修改
    graph.json
    ;禁止为同一个 goal 创建新 graph。
  • RULE-07 (MUST):明确说明无法完成的功能:文件中未暴露的隐式 coupling;agent 中途死亡后的自动 rollback;与 Orca ledger 双向同步;超过约 500 个 node 的 atlas 需要 graphviz;allow-list 仅检查 filesystem,不检查 network/process/secret access。
  • 能力:读取 PLAN 和项目文件;写入 append-only graph store 及文件锁;spawn 并监控 agent process(按 pid 执行 heartbeat);运行 verify/qc 命令;读取 git diff 以检查 allow-list;生成静态 HTML。可选地向外部协调 ledger 进行单向 mirror。

Failure boundaries

失败边界

  • Chưa có PLAN → blocked, gọi
    plan
    (hoặc
    /propose
    rồi
    /plan
    ); là sự cố → chuyển
    orca-issue
    .
  • Cycle (
    check-cycles
    rc 2) hoặc vượt depth ≤ 6 / ≤ 20 node → tool từ chối, blocked tới khi giảm scope.
  • Deps
    gợi-ý
    chưa xác nhận → clarify với user trước khi dispatch lớp đó.
  • Node
    blocked
    (HITL) → chờ người, KHÔNG dispatch headless.
  • Agent im lặng quá lease →
    unknown
    (không phải
    failed
    ) →
    reconcile
    ; quá 3 attempt → failed.
  • Kết quả gen cũ hoặc plan_version khác → STALE, không publish.
  • Không có nguồn cho câu trả lời → nhãn
    không-biết
    , không bịa.
  • 没有 PLAN → blocked,调用
    plan
    (或
    /propose
    ,然后
    /plan
    );属于故障 → 转移到
    orca-issue
    。
  • Cycle(
    check-cycles
    rc 2),或超过 depth 6/node 数 20 → tool 拒绝执行,blocked,直到缩小范围。
  • 尚未确认的
    gợi-ý
    deps → dispatch 对应层之前,向用户 clarify。
  • blocked
    node(HITL)→ 等待人员,禁止 headless dispatch。
  • Agent 超过 lease 仍无响应 →
    unknown
    (不是
    failed
    )→
    reconcile
    ;超过 3 次 attempt → failed。
  • 旧 generation 的结果或不同的 plan_version → STALE,不得 publish。
  • 回答没有来源 → 标签为
    không-biết
    ,不得捏造。

HOW

HOW

Main workflow

主工作流

StepTypeInputsActionOutputs/exitFailure/next
W01deterministicrepo có harnessBước 0: pre-work sweep
pull-gate-sweep.sh
sweep xongkhông harness → bỏ
W02judgmentPLANBước 1: PLAN có chưa; chưa → skill
plan
; điền Depends + Verify thật
PLAN.mdthiếu Depends → tool suy, nhãn gợi-ý
W03deterministicPLAN.mdBước 2:
python3 harness/scripts/orca-graph.py build <PLAN.md>
graph.json + cảnh báo cycle, xung đột filexung đột → thêm Depends hoặc chấp nhận có lý do
W03bdeterministicgraph.jsonBước 2b:
audit-edges <id>
— cạnh thiếu lý do, cạnh preference bỏ được, critical path trước/sau
bảng finding (chỉ đọc)
EDGE_UNJUSTIFIED
→ hỏi user lý do, điền vào Depends
W04judgmentgraphBước 3: 5 câu hỏi bằng
ask
trước, model sau qua
answer
kèm nhãn + nguồn
answer có nhãnkhông nguồn → không-biết
W05effectgraph.jsonBước 4: vẽ
graph-viz.py
→ gửi HTML cho user duyệt (
gate-create
)
HTML + gatekind lạ → B06
W06effectgraph đã duyệtBước 5: vòng
next
→
lock
→
set dispatched
→ dispatch →
set done
tới khi
next
báo hoàn tất
node donelease hết → B05
W07deterministicgraph xongBước 6:
audit <id>
→
graph-atlas.py llmwiki/graph/
→ problem-tree nếu lộ vấn đề
audit-log + atlasbịa > 0 → báo
Chi tiết từng bước (nguồn chân lý cho W01–W07; bước 0–6 ứng với W01–W07):
  1. Pre-work sweep như orca-workflow (
    pull-gate-sweep.sh
    ) nếu có harness.
  2. PLAN có chưa? Chưa → gọi skill
    plan
    . Khuôn
    /plan
    có dòng
    **Depends:** Task 1, Task 3
    và
    **Verify:** <lệnh rc 0>
    — điền thật; thiếu Depends thì tool SUY từ Consumes/Produces và gắn nhãn
    gợi-ý
    .
  3. Dựng graph:
    python3 harness/scripts/orca-graph.py build <PLAN.md>
    → in cycle, deps suy luận, và xung đột ghi cùng file giữa 2 node song song (⚠ → thêm Depends để ép tuần tự, hoặc chấp nhận có lý do).
  4. Trả lời 5 câu hỏi — bằng tool trước, model sau:
    • ask <id> needs
      ·
      ask <id> parallel
      ·
      ask <id> deps <n>
      ·
      ask <id> why <n>
      ·
      ask <id> related
      .
    • Phần model bổ sung (ý nghĩa, liên hệ ngữ nghĩa với graph cũ, rủi ro) → ghi bằng
      answer
      kèm nhãn + nguồn:
      answer <id> <n> --q why --label chắc|gợi-ý|không-biết --score S --evidence file:path:line edge:a->b event:<op_key> absence:<lệnh> --text "..."
      .
    • Rubric (user chốt 2026-09-12): đúng 1 · sai 0 · không-biết 0.3 · gợi-ý có nguồn thật 0.5 · bịa nguồn 0. Không chắc → nói
      gợi-ý
      /
      không-biết
      , đừng gắn
      chắc
      .
  5. Vẽ + gate:
    python3 fdk/tools/graph-viz.py llmwiki/graph/<id>.graph.json
    → gửi HTML cho user duyệt (
    gate-create
    như orca-workflow).
    • Node trên đồ thị vẽ theo kind của task (
      **Kind:** build|test|fix|research|docs|design|review|security|infra|data|migrate|deploy|release|cleanup|integration|wiki
      trong PLAN.md, mặc định
      build
      ) — icon + shape + màu nền tra ở
      engine/kind-glyphs.json
      của repo engine (
      ~/.orca-graph/repo/engine/
      ; sổ mặc định DÙNG CHUNG mọi graph — sửa/thêm qua PR vào repo đó). Viền node vẫn là state (không đụng).
    • kind
      lạ chưa có trong sổ → tool tự sinh tạm (monogram + màu/hình theo hash, ghi vào
      ~/.orca-graph/kind-glyphs.local.json
      — máy-local, không bẩn git clone của engine) và in cảnh báo ra stderr. Thấy cảnh báo này → hỏi user có muốn
      /raise-issue
      để submit glyph mới vào
      kind-glyphs.json
      không; đừng tự ý thêm vào sổ mặc định mà không hỏi.
  6. Vòng chạy (lặp tới khi
    next
    báo hoàn tất):
    next <id>                                  # node ready = chạy song song NGAY; blocked = HITL, KHÔNG dispatch headless
    lock <id> <n> --by <agent>                 # O_EXCL + lease (mặc định 90 phút); heartbeat <id> <n> khi chờ lâu
    set <id> <n> dispatched --op-key <uuid>    # rồi orca orchestration dispatch --task … --inject (brief NGUYÊN VĂN từ PLAN)
    set <id> <n> done --gen <gen> --op-key <uuid>   # gen lấy từ output lệnh dispatched; gen cũ → STALE, không publish
    Agent im lặng quá lease →
    next
    tự đẩy node về
    unknown
    →
    reconcile <id> <n>
    (chạy verify) trước khi lock lại. Tối đa 3 attempt. Muốn mirror sang sổ Orca:
    sync-orca <id> --run
    (một chiều; sổ Orca runtime-global, đóng dấu dự án).
  7. Kết:
    audit <id>
    (mở lại từng nguồn; bịa = 0; ghi
    audit-log.jsonl
    ) →
    graph-atlas.py llmwiki/graph/
    regen atlas → cập nhật problem-tree nếu lộ vấn đề quy trình.
StepTypeInputsActionOutputs/exitFailure/next
W01确定性存在 harness 的 repo步骤 0:执行 pre-work sweep
pull-gate-sweep.sh
sweep 完成没有 harness → 跳过
W02判断PLAN步骤 1:检查是否存在 PLAN;不存在 → skill
plan
;填写真实的 Depends + Verify
PLAN.md缺少 Depends → tool 推断,标签为 gợi-ý
W03确定性PLAN.md步骤 2:
python3 harness/scripts/orca-graph.py build <PLAN.md>
graph.json + cycle、文件冲突警告冲突 → 添加 Depends 或接受有充分理由的冲突
W03b确定性graph.json步骤 2b:
audit-edges <id>
——缺少原因的边、可移除的 preference 边、前后 critical path
finding 表格(只读)
EDGE_UNJUSTIFIED
→ 询问用户原因,填写到 Depends
W04判断graph步骤 3:先使用
ask
回答 5 个问题,随后 model 通过
answer
提交标签 + 来源
带标签的 answer没有来源 → không-biết
W05执行graph.json步骤 4:绘制
graph-viz.py
→ 将 HTML 交给用户审批(
gate-create
)
HTML + gate未知 kind → B06
W06执行已审批的 graph步骤 5:循环
next
→
lock
→
set dispatched
→ dispatch →
set done
,直到
next
报告完成
node donelease 过期 → B05
W07确定性已完成的 graph步骤 6:
audit <id>
→
graph-atlas.py llmwiki/graph/
→ 如发现问题则更新 problem-tree
audit-log + atlas捏造数 > 0 → 报告
各步骤详情(是 W01–W07 的真实来源;步骤 0–6 对应 W01–W07):
  1. 如果存在 harness,按 orca-workflow 的方式执行 Pre-work sweep(
    pull-gate-sweep.sh
    )。
  2. PLAN 是否存在? 不存在 → 调用 skill
    plan
    。
    /plan
    模板包含
    **Depends:** Task 1, Task 3
    和
    **Verify:** <rc 0 命令>
    行——必须如实填写;缺少 Depends 时,tool 根据 Consumes/Produces 推断,并标记为
    gợi-ý
    。
  3. 构建 graph:
    python3 harness/scripts/orca-graph.py build <PLAN.md>
    → 输出 cycle、推断出的 deps,以及两个并行 node 之间的同文件写入冲突(⚠ → 添加 Depends 强制串行,或接受有充分理由的冲突)。
  4. 回答 5 个问题——tool 在前,model 在后:
    • ask <id> needs
      ·
      ask <id> parallel
      ·
      ask <id> deps <n>
      ·
      ask <id> why <n>
      ·
      ask <id> related
      。
    • model 补充的部分(含义、与旧 graph 的语义关系、风险)→ 通过
      answer
      写入
      ,并附带标签和来源:
      answer <id> <n> --q why --label chắc|gợi-ý|không-biết --score S --evidence file:path:line edge:a->b event:<op_key> absence:<lệnh> --text "..."
      。
    • Rubric(用户于 2026-09-12 确认):正确 1 · 错误 0 · 未知 0.3 · 有真实来源的建议 0.5 · 捏造来源 0。不确定时 → 使用
      gợi-ý
      /
      không-biết
      ,不要标记为
      chắc
      。
  5. 绘图 + gate:
    python3 fdk/tools/graph-viz.py llmwiki/graph/<id>.graph.json
    → 将 HTML 交给用户审批(与 orca-workflow 相同的
    gate-create
    )。
    • Graph 中的 node 根据 task 的 kind 绘制(PLAN.md 中的
      **Kind:** build|test|fix|research|docs|design|review|security|infra|data|migrate|deploy|release|cleanup|integration|wiki
      ,默认
      build
      )——icon、shape 和背景色查表自 engine repo 中的
      engine/kind-glyphs.json
      (
      ~/.orca-graph/repo/engine/
      ;默认 ledger 被所有 graph 共享——通过向该 repo 提交 PR 来修改或新增条目)。node 边框仍表示 state(保持不变)。
    • 默认 ledger 中尚无的
      kind
      → tool 自动生成临时 glyph(monogram + 基于 hash 的颜色/形状),并写入
      ~/.orca-graph/kind-glyphs.local.json
      (machine-local,不污染 engine 的 git clone),同时向 stderr 打印警告。看到此警告 → 询问用户是否要通过
      /raise-issue
      提交新 glyph 到
      kind-glyphs.json
      ;不要在未经询问的情况下自行添加到默认 ledger。
  6. 执行循环(重复直到
    next
    报告完成):
    undefined
next <id> # node ready = chạy song song NGAY; blocked = HITL, KHÔNG dispatch headless lock <id> <n> --by <agent> # O_EXCL + lease (mặc định 90 phút); heartbeat <id> <n> khi chờ lâu set <id> <n> dispatched --op-key <uuid> # rồi orca orchestration dispatch --task … --inject (brief NGUYÊN VĂN từ PLAN) set <id> <n> done --gen <gen> --op-key <uuid> # gen lấy từ output lệnh dispatched; gen cũ → STALE, không publish
Agent 超过 lease 仍无响应 → `next` 自动将 node 推进到 `unknown` → `reconcile <id> <n>`(运行 verify),然后才能重新 lock。最多 3 次 attempt。
如需 mirror 到 Orca ledger:`sync-orca <id> --run`(单向;Orca ledger 是 runtime-global,并带有项目标记)。
6. **结束:** `audit <id>`(重新打开每个来源;捏造数 = 0;写入 `audit-log.jsonl`)→ 运行 `graph-atlas.py llmwiki/graph/` 重新生成 atlas → 如果发现流程问题,则更新 problem-tree。

Branches

分支

IDKindGuardHành viSkip / failureRejoin
B01user_optionalviệc cần tách graph con dưới một node
build <PLAN> --parent <gid>/<node>
; node mẹ join khi MỌI node con xong
vượt depth 6 hoặc 20 node → tool từ chốiW03
B02conditional_required
build
lại trên graph đã có
plan_version + 1
, node bỏ vào
superseded[]
, node đổi
spec_hash
đã xong →
fresh=stale
kết quả plan_version cũ → STALEW06
B03user_optionaluser muốn dừng / tiếp / huỷ
control <id>
pause, resume, cancel, status
cancelled
không resume → build plan mới
W06
B04capability_optionalmuốn một lệnh thay 4 lệnh gõ tay
run <id> <node> -- <lệnh agent>
+ daemon
watch
+ control-room
node thiếu verify → từ chối headlessW06
B05recoveryagent im lặng quá lease
next
đẩy node về
unknown
→
reconcile <id> <n>
chạy verify rồi mới lock lại
tối đa 3 attempt rồi failedW06
B06conditional_required
kind
lạ chưa có trong
kind-glyphs.json
tool sinh glyph tạm vào
kind-glyphs.local.json
+ cảnh báo stderr → hỏi user có
/raise-issue
glyph mới không
không tự thêm vào sổ mặc địnhW05
B07user_optionalmuốn mirror sang sổ Orca
sync-orca <id> --run
(một chiều)
—W06
B09user_optionaluser yêu cầu thêm việc / "vẽ thêm node" khi graph đã có
add-node <id> --title … [--depends t1:data] [--blocks t5] [--files …] [--verify …] [--kind …] [--resources …]
→ in
+ tN
, build lại, vẽ lại HTML, đưa link cho user
sinh cycle / > 20 node / dep lạ → tool từ chối, PLAN nguyên vẹnW05
B10recovery
lock
báo
chờ RESOURCE
node khác đang giữ claim xung đột → làm node ready khác trước,
ask <id> waiting
xem ai giữ; lock lại khi node kia xong
không tự
unlock
node của agent khác
W06
B08conditional_requirednode khai
**QC:**
chạy QC độc lập sau verify rc 0; fail →
done_unverified
(run/set) hoặc
ready
(reconcile)
không khai → hành vi cũW06
IDKindGuard行为Skip / failureRejoin
B01user_optional需要将工作拆分到某个 node 下的子 graph
build <PLAN> --parent <gid>/<node>
;父 node 在所有子 node 完成后 join
超过 depth 6 或 20 个 node → tool 拒绝W03
B02conditional_required对已有 graph 重新
build
plan_version + 1
,被移除的 node 进入
superseded[]
,已完成的 node 若
spec_hash
改变 →
fresh=stale
旧 plan_version 的结果 → STALEW06
B03user_optional用户希望暂停/继续/取消
control <id>
pause、resume、cancel、status
cancelled
不可 resume → 创建一个新的 plan
W06
B04capability_optional希望用一条命令代替 4 条手动命令
run <id> <node> -- <agent 命令>
+ daemon
watch
+ control-room
node 缺少 verify → headless 拒绝W06
B05recoveryagent 超过 lease 仍无响应
next
将 node 推进到
unknown
→
reconcile <id> <n>
运行 verify,然后才能重新 lock
最多 3 次 attempt,之后标记 failedW06
B06conditional_required
kind
尚未出现在
kind-glyphs.json
tool 生成临时 glyph 并写入
kind-glyphs.local.json
+ 向 stderr 警告 → 询问用户是否要
/raise-issue
提交新 glyph
不得自行添加到默认 ledgerW05
B07user_optional希望 mirror 到 Orca ledger
sync-orca <id> --run
(单向)
—W06
B09user_optionalgraph 已存在时,用户要求添加工作/“再画一个 node”
add-node <id> --title … [--depends t1:data] [--blocks t5] [--files …] [--verify …] [--kind …] [--resources …]
→ 输出
+ tN
,重新 build,重新绘制 HTML,并将链接交给用户
产生 cycle/超过 20 个 node/未知 dep → tool 拒绝,PLAN 保持不变W05
B10recovery
lock
报告“等待 RESOURCE”
其他 node 正持有冲突 claim → 先执行另一个 ready node,通过
ask <id> waiting
查看持有者;对方完成后重新 lock
不得自行
unlock
另一个 agent 的 node
W06
B08conditional_requirednode 声明了
**QC:**
verify rc=0 后运行独立 QC;失败 →
done_unverified
(run/set)或
ready
(reconcile)
未声明 → 保持旧行为W06

Validation và stopping

验证与停止条件

Tất định:
done
chỉ khi
verify
rc 0 (và QC nếu khai); lease/generation/op_key/CAS do tool quyết;
check-cycles
và
lint
/
build --strict
rc 2 khi hỏng;
audit
mở lại từng nguồn, bịa = 0. Cần người: duyệt HTML graph ở gate, xác nhận deps
gợi-ý
, xử lý node
blocked
. Vòng chạy dừng khi
next
báo hoàn tất; mỗi node tối đa 3 attempt.
确定性条件:只有 verify rc 0(且声明了 QC 时 QC 通过)才能标记
done
;lease/generation/op_key/CAS 由 tool 决定;
check-cycles
以及
lint
/
build --strict
在损坏时返回 rc 2;
audit
重新打开每个来源,捏造数 = 0。需要人工介入:审批 HTML graph、确认
gợi-ý
deps、处理
blocked
node。执行循环在
next
报告完成时停止;每个 node 最多 3 次 attempt。

Examples

示例

  • Positive: PLAN 5 task, t2 và t3 cùng Depends t1 →
    build
    báo không cycle, không xung đột file →
    ask t2 parallel
    trả t3 →
    next
    cấp t1, xong thì cấp t2 + t3 song song mỗi cái một
    lock --by
    ,
    set done --gen
    →
    audit
    bịa = 0 → atlas regen.
  • Boundary/failure: t2 và t3 song song cùng ghi
    src/api.ts
    →
    build
    in ⚠ xung đột ghi cùng file → thêm
    **Depends:** Task 2
    vào t3 để ép tuần tự rồi build lại; agent t3 im quá lease →
    unknown
    →
    reconcile
    chạy verify trước khi lock lại.
  • Boundary: model muốn nói "t4 tồn tại để mở khoá release" nhưng không có nguồn mở được →
    answer … --label không-biết
    (0.3), không gắn
    chắc
    .
  • Positive: PLAN 包含 5 个 task,t2 和 t3 都依赖 t1 →
    build
    报告没有 cycle、没有文件冲突 →
    ask t2 parallel
    返回 t3 →
    next
    先分配 t1,完成后同时分配 t2 + t3,每个都使用独立的
    lock --by
    ,然后执行
    set done --gen
    →
    audit
    捏造数 = 0 → 重新生成 atlas。
  • Boundary/failure: t2 和 t3 并行且同时写入
    src/api.ts
    →
    build
    输出 ⚠ 同文件写入冲突 → 在 t3 中添加
    **Depends:** Task 2
    强制串行,然后重新 build;t3 agent 超过 lease 仍无响应 →
    unknown
    →
    reconcile
    运行 verify,然后才能重新 lock。
  • Boundary: model 想说“t4 的存在是为了解锁 release”,但没有可打开的来源 →
    answer … --label không-biết
    (0.3),不得标记为
    chắc
    。

Reference — Phân cấp graph mẹ → con (PRD Reprise Graph Engine §4)

Reference — 父 graph → 子 graph 分层(PRD Reprise Graph Engine §4)

  • build <PLAN> --parent <gid>/<node>
    → graph con gắn vào một node của graph mẹ (containment tree, KHÁC dependency DAG). Node mẹ có
    child_graph
    , join tự động: chỉ
    done_unverified
    khi MỌI node con xong (invariant 4); con có node
    blocked
    → mẹ
    blocked
    .
  • Giới hạn cứng: depth ≤ 6, ≤ 20 node/graph. Vượt → tool từ chối, giảm scope thay vì đào sâu.
  • Deps xuyên graph:
    **Depends:** other-graph/t3
    — thoả khi node đó xong ở graph kia.
    check-cycles [dir]
    gộp mọi graph, in ĐƯỜNG cycle cụ thể (
    a/t2 → b/t3 → a/t2
    ), rc 2 (PRD §5.3).
  • lint <id>
    — leaf đủ hợp đồng chưa (PRD §4.4): title · files · produces · verify · deps rõ.
    build --strict
    rc 2 nếu thiếu verify/files.
  • build <PLAN> --parent <gid>/<node>
    → 子 graph 挂载到父 graph 的一个 node(containment tree,与 dependency DAG 不同)。父 node 拥有
    child_graph
    ,并自动 join:只有在所有子 node 完成后才进入
    done_unverified
    (invariant 4);子 node 中存在
    blocked
    → 父 node 为
    blocked
    。
  • 硬性限制:depth ≤ 6,每个 graph ≤ 20 个 node。超过限制 → tool 拒绝执行,应缩小范围,而不是继续深入。
  • 跨 graph deps:
    **Depends:** other-graph/t3
    ——当另一个 graph 中该 node 完成时满足。
    check-cycles [dir]
    合并检查所有 graph,输出具体 cycle 路径(
    a/t2 → b/t3 → a/t2
    ),返回 rc 2(PRD §5.3)。
  • lint <id>
    ——检查 leaf node 的契约是否完整(PRD §4.4):title · files · produces · verify · deps 是否明确。
    build --strict
    在缺少 verify/files 时返回 rc 2。

Reference — Topology có lý do & tài nguyên có chủ (PRD v1.1 §23)

Reference — 有原因的 topology 与受控资源(PRD v1.1 §23)

  • Depends parse NGHIÊM: token không resolve được (ghi chú chen vào sau dấu
    —
    ,
    Task 1 và Task 2
    , task không tồn tại, dep xuyên graph sai dạng
    <gid>/<tid>
    ) là LỖI
    build
    , không bị nuốt — cạnh biến mất im lặng thì node ready sớm mà không ai thấy. Ngăn bằng
    ,
    hoặc
    ;
    ; ghi chú để ở dòng khác.
  • Lý do cạnh:
    **Depends:** Task 1 (data), other-graph/t3 (control)
    . Năm lớp cứng (data · contract · acceptance · effect_order · control) không bỏ được dù không truyền artifact — cổng duyệt không mang payload vẫn là cạnh thật.
    preference
    = chỉ do thứ tự viết. Reason KHÔNG nằm trong
    spec_hash
    : gắn lý do cho graph đang chạy không làm node đã xong thành stale.
  • audit-edges <id> [--json] [--strict]
    — dry-run. Mã finding:
    EDGE_UNJUSTIFIED
    (khai Depends mà thiếu lý do → giữ) ·
    EDGE_INFERRED
    (deps suy luận) ·
    PREFERENCE_REMOVABLE
    (đề xuất bỏ) ·
    PREFERENCE_HAS_HIDDEN_CONSTRAINT
    (ghi preference nhưng Consumes/Verify/QC của downstream nhắc tới Task, file hoặc output của upstream, hoặc hai node cùng ghi một file → giữ; so CHUỖI nên coupling không lộ ra chữ thì không bắt được). In critical path đếm theo node (unit-weight, KHÔNG phải thời lượng), số lớp và tập chạy-ngay trước/sau.
    --strict
    rc 2 khi còn
    EDGE_UNJUSTIFIED
    .
  • Resource claims: key do tool chuẩn hoá (lowercase + normpath) nên alias khác chữ vẫn là một tài nguyên.
    lock
    lấy HẾT claim hoặc không lấy gì (không giữ A chờ B), soi mọi graph trong cùng store, chạy dưới một mutex admission.
    exclusive
    chặn mọi claim cùng key;
    capacity:N
    = KÍCH THƯỚC POOL của key — mỗi node đang giữ key (kể cả
    shared
    ) chiếm 1 slot, các node khai N khác nhau thì lấy N nhỏ nhất (không phụ thuộc thứ tự lock,
    shared
    không lách được quota);
    shared
    thuần chỉ bị exclusive hoặc pool đầy chặn. Lease hết ở graph KHÁC cũng được reaper quét khi
    lock
    /
    next
    (claim không kẹt xuyên graph);
    unlock
    tay một node đang chạy đưa nó về
    unknown
    — reconcile trước khi lock lại.
    build
    in
    ℹ … cùng claim
    cho cặp song song — thông tin, không phải lỗi.
  • ask <id> waiting
    — mỗi node chưa chạy kèm MỘT lý do:
    data
    (chờ upstream) ·
    gate
    (HITL, cổng control/acceptance, verify chưa xanh, unknown chờ reconcile) ·
    resource
    (claim bị giữ, nêu ai giữ) ·
    queue
    (max_parallel đầy) ·
    control
    (pause/cancel) ·
    retry
    (hết 3 attempt) ·
    none
    .
    next
    in thêm dòng cho node ready nhưng chưa lock được — ready ≠ admitted.
  • Lớp topo (
    ask parallel
    ) là hình chiếu để giải thích, không phải rào: node đủ deps là ready ngay dù node khác cùng lớp với upstream của nó chưa xong.
  • 严格解析 Depends: 无法解析的 token(插在破折号后的注释、
    Task 1 和 Task 2
    、不存在的 task、格式错误的跨 graph dep
    <gid>/<tid>
    )均为
    build
    错误,不能被静默忽略——否则边会悄悄消失,导致 node 过早 ready 且无人察觉。使用
    ,
    或
    ;
    分隔;注释写在其他行。
  • 边的原因:
    **Depends:** Task 1 (data), other-graph/t3 (control)
    。五种硬层级(data · contract · acceptance · effect_order · control)即使没有传递 artifact 也不能移除——不携带 payload 的审批 gate 仍是真实的边。
    preference
    仅表示因书写顺序产生的依赖。原因不纳入
    spec_hash
    :为正在运行的 graph 添加原因,不会使已完成的 node 变成 stale。
  • audit-edges <id> [--json] [--strict]
    ——dry-run。Finding 代码:
    EDGE_UNJUSTIFIED
    (声明了 Depends 但缺少原因 → 保留)·
    EDGE_INFERRED
    (推断出的 deps)·
    PREFERENCE_REMOVABLE
    (建议移除)·
    PREFERENCE_HAS_HIDDEN_CONSTRAINT
    (虽然记录为 preference,但 downstream 的 Consumes/Verify/QC 引用了 upstream 的 Task、文件或输出,或者两个 node 写入同一文件 → 保留;由于比较的是字符串,无法发现未显式暴露的 coupling)。输出按 node 计数的 critical path(unit-weight,不是时长)、层数,以及前后可立即运行的 node 集合。仍有
    EDGE_UNJUSTIFIED
    时,
    --strict
    返回 rc 2。
  • Resource claims: key 由 tool 标准化(lowercase + normpath),因此拼写不同但含义相同的 alias 会归为同一资源。
    lock
    要么获取全部 claim,要么一个都不获取(不能只持有 A 并等待 B);检查同一 store 中的所有 graph,并在单个 mutex admission 下执行。
    exclusive
    阻止同一 key 的所有 claim;
    capacity:N
    表示该 key 的 pool 容量——每个持有该 key 的 node(即使为
    shared
    )都占用 1 个 slot,各 node 声明不同 N 时取最小值(不依赖 lock 顺序,
    shared
    也不能绕过 quota);纯
    shared
    只会被
    exclusive
    或已满的 pool 阻止。其他 graph 中的 lease 过期,也可由 reaper 在
    lock
    /
    next
    时扫描清理(claim 不会跨 graph 卡住);手动
    unlock
    一个正在运行的 node 会将其转为
    unknown
    ——必须先 reconcile 才能重新 lock。
    build
    会为并行 claim 相同的 node 对输出
    ℹ … cùng claim
    ;这是信息,不是错误。
  • ask <id> waiting
    ——为每个尚未运行的 node 给出一个原因:
    data
    (等待 upstream)·
    gate
    (HITL、control/acceptance gate、verify 尚未通过、unknown 等待 reconcile)·
    resource
    (claim 被占用,并说明持有者)·
    queue
    (max_parallel 已满)·
    control
    (pause/cancel)·
    retry
    (已用完 3 次 attempt)·
    none
    。
    next
    还会为已 ready 但无法 lock 的 node 输出一行信息——ready ≠ admitted。
  • 拓扑层(
    ask parallel
    )是用于解释的投影,不是硬性屏障:只要依赖满足,node 立即 ready,即使同层其他 node 的 upstream 尚未完成。

Reference — Định danh, vòng khô, ngân sách lần gọi (PRD v1.1 §24–27)

Reference — 标识、无环与调用预算(PRD v1.1 §24–27)

  • reconcile-items --expected A,B,C --verdicts rows.jsonl [--universe N]
    — ghép verdict (
    supported|refuted|inconclusive
    ) theo
    item_id
    , không theo vị trí.
    {A,A,B}
    đủ 3 dòng vẫn THIẾU C → rc 2. Dòng
    verdict: null
    hoặc
    status
    ≠ ok = outcome thiếu CÓ ID (
    errored_ids
    ), không bị lọc mất, không tính refuted; cùng item vừa có verdict vừa có dòng lỗi →
    CONFLICTING_OUTCOME
    ; manifest rỗng cần
    --allow-empty
    ; thiếu file verdict là lỗi, không phải "0 dòng".
    coverage
    tách hai mẫu số: xong/đã-chọn và đã-chọn/toàn-tập (
    unknown
    khi không biết — không báo 100%). Dùng khi fan-out một lô item (vd
    /tc-run
    ) rồi gom kết quả.
  • dry-streak --prev N --complete 0|1 --new N
    — vòng discovery khô chỉ tính khi vòng HOÀN TẤT và không có ứng viên mới; vòng lỗi reset về 0. Khô = heuristic dừng, không chứng minh đã rà hết.
  • cost-envelope <id> [--reviewers N] [--max-attempts N]
    — đếm LẦN GỌI model trước dispatch: planner 1 + worker/node afk + reviewer × node có QC + synthesis 1;
    max_calls
    nhân trần retry;
    expected
    ghi unknown khi chưa có số đo. Verify shell = 0 token nhưng vẫn tốn CPU, báo riêng. Đừng nói "N agent" thay tổng call.
  • reconcile-items --expected A,B,C --verdicts rows.jsonl [--universe N]
    ——根据
    item_id
    匹配 verdict(supported|refuted|inconclusive),而不是根据位置。
    {A,A,B}
    即使有 3 行,仍表示缺少 C → rc 2。
    verdict: null
    或
    status
    ≠ ok 表示缺少带 ID 的结果(
    errored_ids
    ),不能被过滤掉,也不能计为 refuted;同一 item 同时有 verdict 和错误行 →
    CONFLICTING_OUTCOME
    ;空 manifest 需要
    --allow-empty
    ;缺少 verdict 文件属于错误,不能报告为“0 行”。
    coverage
    拆分为两个分母:已完成/已选择,以及已选择/全集(未知时填
    unknown
    ,不能报告为 100%)。适用于 fan-out 一批 item(例如
    /tc-run
    )后汇总结果的场景。
  • dry-streak --prev N --complete 0|1 --new N
    ——dry discovery streak 只有在整轮完成且没有新候选时才计数;发生错误时重置为 0。dry 仅表示使用 heuristic 停止,不能证明已经检查全部内容。
  • cost-envelope <id> [--reviewers N] [--max-attempts N]
    ——统计 dispatch 前的 model 调用次数:planner 1 + worker/node afk + 含 QC 的 node reviewer × node + synthesis 1;
    max_calls
    按 retry 次数向上取整相乘;尚无测量值时,
    expected
    记为 unknown。Verify shell = 0 token,但仍消耗 CPU,应单独报告。不要用“N agent”代替总调用次数。

Reference — Replan không phá lịch sử (PRD §10)

Reference — Replan 不破坏历史(PRD §10)

  • build
    lại trên graph đã có =
    plan_version + 1
    ; node bị bỏ vào
    superseded[]
    (giữ state cuối), node đổi hợp đồng (
    spec_hash
    = title/files/deps/verify/produces) mà đã xong →
    fresh=stale
    (chỉ cảnh báo, không lùi state).
  • Kết quả cũ:
    set done --plan-version N
    với N ≠ hiện tại → STALE, không publish (invariant 2).
  • run
    nhớ
    plan_version
    lúc dispatch: replan xảy ra GIỮA lúc agent chạy → kết quả là STALE, node về
    ready
    để làm lại theo spec mới (rc ≠ 0).
  • add-node
    là replan một-node: chạy dưới mutex admission (hai lệnh song song không đè nhau), nhìn PLAN đúng như parser (bỏ qua code fence), mọi field phải MỘT dòng,
    --blocks
    từ chối node đang
    locked|dispatched
    , PLAN phải khớp graph (sửa tay thì
    build
    trước); id mới không tái dùng id node đã bị bỏ;
    --blocks t5
    chèn node mới TRƯỚC t5 (nối vào dòng Depends của t5, chưa có thì thêm). Build lại graph CON mà quên
    --parent
    vẫn giữ liên kết mẹ cũ.
  • 对已有 graph 重新
    build
    =
    plan_version + 1
    ;被移除的 node 进入
    superseded[]
    (保留最终 state);已完成的 node 若契约改变(
    spec_hash
    = title/files/deps/verify/produces),则
    fresh=stale
    (仅警告,不回退 state)。
  • 旧结果:使用与当前值不同的
    set done --plan-version N
    → STALE,不得 publish(invariant 2)。
  • run
    会记住 dispatch 时的
    plan_version
    :如果 agent 运行期间发生 replan → 结果为 STALE,node 回到
    ready
    ,按新 spec 重做(rc ≠ 0)。
  • add-node
    是一次单 node replan:在 mutex admission 下执行(两个并行命令不会互相覆盖),像 parser 一样读取 PLAN(忽略 code fence),每个 field 必须只有一行;
    --blocks
    拒绝指向处于
    locked|dispatched
    的 node;PLAN 必须与 graph 匹配(若被手动修改,先执行
    build
    );新 id 不得复用已移除 node 的 id;
    --blocks t5
    会将新 node 插入 t5 之前(连接到 t5 的 Depends 行;如果该行不存在则创建)。重新 build 子 graph 时即使忘记
    --parent
    ,仍会保留原父级链接。

Reference — Control (PRD §8.3, invariant 11)

Reference — Control(PRD §8.3,invariant 11)

  • control <id> pause|resume|cancel|status
    . "Yêu cầu" ≠ "đã dừng":
    pause_requested
    chỉ thành
    paused
    khi không còn node
    locked|dispatched
    ;
    next
    /
    lock
    không cấp node mới khi không
    active
    .
    cancelled
    không resume — build plan version mới.
  • build --max-parallel N
    (mặc định 4):
    lock
    từ chối khi số node đang chạy đã đủ (PRD §12.1).
  • control <id> pause|resume|cancel|status
    。“已请求”不等于“已停止”:只有在不存在
    locked|dispatched
    node 时,
    pause_requested
    才会变为
    paused
    ;当 graph 不处于 active 状态时,
    next
    /
    lock
    不再分配新 node。
    cancelled
    不可 resume——需要创建新的 plan version。
  • build --max-parallel N
    (默认 4):正在运行的 node 数量达到上限后,
    lock
    将被拒绝(PRD §12.1)。

Reference — Daemon & control-room (PRD §8.4: lease 60 s · heartbeat 15 s · reaper 15 s)

Reference — Daemon 与 control-room(PRD §8.4:lease 60 秒 · heartbeat 15 秒 · reaper 15 秒)

  • run <id> <node> [--hb 15] [--lease-sec 60] [--strict] -- <lệnh agent>
    — thay 4 lệnh gõ tay: lock ngắn → dispatched → spawn lệnh → heartbeat theo pid → exit 0 thành
    done
    (verify tự chạy), khác 0 thành
    failed
    . Node không có
    verify
    bị từ chối headless (
    --allow-unverified
    để ép). Tự ghi thư mục vào registry
    ~/.orca-graph/registry.json
    và tự spawn daemon nếu chưa có (
    ORCA_GRAPH_NO_DAEMON=1
    để tắt,
    ORCA_GRAPH_HOME
    đổi thư mục nhà).
  • Allow-list ghi (GH#162): khi trong git repo,
    run
    diff file THẬT bị đổi (tracked sửa + untracked mới, so với NGAY TRƯỚC lúc spawn) với
    files
    khai của node. Ngoài phạm vi → mặc định chỉ CẢNH BÁO (ghi vào
    note
    của event
    done
    );
    --strict
    mới phục hồi cứng (untracked mới bị xoá, tracked sửa bị
    git checkout
    về HEAD). Không phải git repo (vd store nằm ngoài repo) → tự bỏ qua, không lỗi. Bookkeeping của CHÍNH orca-graph (
    .graph.json
    /
    .events.jsonl
    /
    .locks/
    ) luôn bị loại khỏi diff, không tính là "agent ghi".
  • watch [--once] [--interval 5] [--idle-sec 600]
    — một daemon cho cả máy, lock
    daemon.lock
    theo pid. Mỗi lượt chỉ đọc các dir trong registry còn node chạy (chi phí theo số node chạy, không theo số dự án mở; đo 84 ms/lượt kể cả khởi động Python): reaper lease hết →
    unknown
    → có verify thì reconcile ngay; in bảng sống/chết; registry rỗng quá idle-sec thì tự thoát; graph đổi thì regen control-room.
  • fdk/tools/build-control-room.py
    →
    llmwiki/html/control-room.html
    — trang đầu tiên mở ra, data-first (chỉ đọc registry, graph.json, problem-tree, tokens.jsonl, audit-log): đang chạy gì toàn máy + trần, tiến độ từng graph + node kẹt, nợ mở, chi phí hôm nay + khoảng cách tự chấm/audit. Tự refresh 5 s; daemon regen mỗi lượt và mỗi lần
    run
    bắt đầu/kết thúc nên trang LIVE không cần server. Bậc 2 (server + bấm pause/cancel) và bậc 3 (nhúng Orca) chưa làm, chỉ làm khi bậc 1 dùng hằng ngày thấy thiếu.
  • Sống/chết ≠ đúng/sai: daemon chỉ biết process còn hay mất;
    done
    hay làm lại vẫn do
    verify
    quyết. Process sống mà treo thì heartbeat vẫn xanh — đặt
    **Verify:**
    idempotent và trần thời gian theo node.
  • run <id> <node> [--hb 15] [--lease-sec 60] [--strict] -- <agent 命令>
    ——用于代替 4 条手动命令:短暂 lock → dispatched → spawn 命令 → 按 pid 执行 heartbeat → exit 0 变为
    done
    (自动运行 verify),非 0 变为
    failed
    。Node 没有 verify 时,headless 会被拒绝(可使用
    --allow-unverified
    强制执行)。自动将目录写入 registry
    ~/.orca-graph/registry.json
    ,并在 daemon 尚未运行时自动 spawn(设置
    ORCA_GRAPH_NO_DAEMON=1
    可关闭,使用
    ORCA_GRAPH_HOME
    更改 home 目录)。
  • 写入 allow-list(GH#162): 位于 git repo 中时,
    run
    会对实际发生变化的文件进行 diff(相对于 spawn 前一刻,包括 tracked 修改和 untracked 新文件),并与 node 声明的
    files
    比较。超出范围 → 默认仅发出警告(写入
    done
    事件的
    note
    );只有
    --strict
    才会执行硬恢复(删除 untracked 新文件,将 tracked 修改通过
    git checkout
    恢复到 HEAD)。不在 git repo 中时(例如 store 位于 repo 外)→ 自动跳过,不报错。orca-graph 自身的 bookkeeping(
    .graph.json
    /
    .events.jsonl
    /
    .locks/
    )始终从 diff 中排除,不计为“agent 写入”。
  • watch [--once] [--interval 5] [--idle-sec 600]
    ——整台机器只使用一个 daemon,通过 pid lock
    daemon.lock
    。每轮只读取 registry 中仍有运行中 node 的目录(开销取决于运行中的 node 数,而不是打开的项目数;实测每轮 84 ms,包含 Python 启动时间):lease 过期时 reaper 将 node 转为
    unknown
    → 如果存在 verify,则立即 reconcile;输出存活/死亡表格;registry 为空的时间超过 idle-sec 后自动退出;graph 发生变化时重新生成 control-room。
  • fdk/tools/build-control-room.py
    →
    llmwiki/html/control-room.html
    ——默认首先打开的页面,采用 data-first 方式(只读取 registry、graph.json、problem-tree、tokens.jsonl、audit-log):整台机器当前正在运行的任务与上限、各 graph 的进度及卡住的 node、尚未偿还的工作量、今日成本,以及与自动评分/audit 的差距。每 5 秒自动刷新;daemon 在每轮及每次
    run
    开始/结束时重新生成,因此 LIVE 页面无需 server。第 2 层(server + pause/cancel 按钮)和第 3 层(嵌入 Orca)尚未实现,只有当第 1 层被日常使用且确认缺少这些能力时才继续构建。
  • 存活/死亡 ≠ 正确/错误:daemon 只能判断 process 是否仍存在;
    done
    还是需要重做,始终由
    verify
    决定。Process 存活但卡住时 heartbeat 仍为绿色——应为每个 node 设置幂等的
    **Verify:**
    和超时限制。

Reference — Recap

Reference — Recap

/orca-graph
= PLAN → graph.json có deps →
ask
trả lời 5 câu hỏi tất định → dispatch theo lớp có khoá/lease/gen → state bền append-only →
answer
/
audit
chấm model theo rubric 1/0/0.3/0.5/bịa=0 → HTML 1 graph + atlas 2D. Use-case bất ngờ: chạy
build
trên PLAN cũ đã làm xong để kiểm lại xem hồi đó có 2 task ghi cùng file mà chạy song song không; hoặc
related
để thấy PLAN mới chạm file nào của PLAN cũ trước khi đụng.
/orca-graph
= PLAN → 带 deps 的 graph.json →
ask
确定性地回答 5 个问题 → 按层调度并配备锁/lease/gen → 持久化 append-only state →
answer
/
audit
按 1/0/0.3/0.5/捏造数=0 的 rubric 评判 model → 单 graph HTML + 2D atlas。 意外用例:对已经完成的旧 PLAN 运行
build
,用于重新检查当时是否存在两个并行写入同一文件的 task;或者使用
related
查看新 PLAN 在修改前触及了旧 PLAN 的哪些文件。