17 · Routines、Pipelines 与自动化¶
一句话结论: Routine 把可重复工作模板化并在触发时创建可审计的 Issue/Run;Pipeline 则把业务对象建成带阶段、版本、租约、blocker、review gate 和自动化 ledger 的独立状态机,再通过 linked Issue 借用 Agent 执行能力。
1. 为什么 Routine 不应只是 Cron + Prompt¶
简单 cron callback 缺少:
- 哪个 Company/Project/Agent 负责;
- 使用哪个版本的说明;
- 本次输入变量和 secret refs;
- 是否已经触发过;
- 创建了哪个 Issue/Run;
- 失败怎样重试;
- 是否可在 UI 审计/手动运行。
Routine 把这些事实持久化,而 cron 只负责“时间到了”。
2. Routine 模型¶
Routine 通常包含:
- company/project;
- title/description/status;
- assignee Agent;
- issue template/status/priority/work mode;
- schedule/trigger;
- variables/env/secret refs;
- execution workspace preference;
- current revision;
- plugin management provenance。
另有 trigger、run、revision、document 等相关对象。
3. 触发类型¶
除了 cron,Routine 还可被手动、webhook、pipeline 或系统事件触发。Trigger 保存:
- kind/config;
- enabled;
- secret/rotation(对 webhook);
- last/next fire;
- idempotency/source metadata。
Cron parser/formatter 独立,使 UI 显示与 Server 计划一致。
4. Routine 执行路径¶
sequenceDiagram
participant T as Timer / Webhook / Manual
participant R as Routine Service
participant DB as PostgreSQL
participant I as Issue Service
participant H as Heartbeat
T->>R: trigger(routine, input, idempotency)
R->>DB: load active routine + revision snapshot
R->>R: resolve variables / env refs / workspace policy
R->>I: create origin=routine_execution Issue
I->>DB: unique origin fingerprint prevents duplicate
R->>DB: persist routine run / linked issue
R->>H: assignment/automation wakeup
H-->>R: queued/coalesced/skipped evidence
真正工作仍作为 Issue + Heartbeat 执行,所以 checkout、预算、权限、workspace 和 recovery 不会被 cron 绕过。
5. Revision Snapshot¶
Routine 被编辑后,历史运行必须知道使用的是哪版模板。Revision snapshot 保存当时的:
-标题/描述; - assignee/config; - variables/env; - workspace/execution options; - schedule/automation contract。
Run 绑定 snapshot,而不是事后读取“当前 Routine”。这对复现失败和 pipeline retry 很重要。
6. Variables 与 Secret¶
Routine variables 有类型和默认/required 规则,触发输入需要校验。Secret 使用 ref,不应作为变量明文写进 revision 或 run context。
解析顺序通常是:
覆盖仍受 schema/type 限制,不能通过输入添加任意 env key。
7. Pipeline 不是 Issue 看板列¶
Pipeline 处理“业务对象在流程阶段中流转”,例如内容生产、候选评审、发布流程。核心对象:
- Pipeline;
- Stage;
- Transition;
- Case;
- Case Event;
- Case Blocker;
- Case ↔ Issue Link;
- Automation Execution;
- Case/Pipeline Document。
Issue 表达工作,Case 表达被流程管理的业务项。一个 Case 可链接多个 Issue,不能把两者合并。
8. Pipeline 定义¶
Pipeline 包含有序 stages 和允许 transitions。Stage 可有:
- kind(普通、review、terminal 等);
- enabled;
- form/required fields;
- transition gate;
- approver/reviewer;
- child breakdown/rollup;
- automation routine;
- workspace/issue template;
- variables。
Transition 显式保存 from/to,不允许 UI 随便把 Case 拖到任意阶段。
9. Case 的并发字段¶
pipeline_cases 重要字段:
stageId、caseKey、fields/summary;version;- parent case/version;
- request key/automation attempt;
- pending suggestion;
- lease owner type/user/agent、token、expiry;
- terminal kind/time;
- retired/hidden;
- child/terminal child count。
Version 处理 optimistic concurrency,lease 处理“谁正在编辑/推进”,两者职责不同。
10. Case Lease¶
stateDiagram-v2
[*] --> Free
Free --> Leased: user/agent acquire token
Leased --> Leased: owner mutation + refresh
Leased --> Free: release
Leased --> Expired: expiresAt passed
Expired --> Leased: next actor acquires
Mutation 要同时验证 actor ownership、lease token 和未过期。Expired lease 可被安全接管,但旧 owner 的晚到请求因 token/version 不匹配而失败。
11. Case Version¶
每次内容/阶段 mutation 增加 version。Client 提交 expected version:
UPDATE pipeline_cases
SET ..., version = version + 1
WHERE id = :id AND version = :expected
RETURNING *;
0 行表示有人先改了 Case,调用方必须 reload/merge,而不是覆盖。
Lease 保护临时所有权,version 保护跨请求的内容事实。
12. Transition Gate¶
进入目标 stage 前可能检查:
- transition 存在且 stage enabled;
- actor 有权限/lease;
- required fields 完整;
- blockers resolved;
- child rollup 满足;
- review approval 仍对应当前 version;
- pending suggestion 已处理;
- automation/retry state允许。
flowchart LR
FROM["Current Stage"] --> EDGE{"transition exists"}
EDGE --> FORM{"required fields"}
FORM --> BLOCK{"blockers"}
BLOCK --> CHILD{"children gate"}
CHILD --> REVIEW{"review / approval current"}
REVIEW --> CAS["versioned transition transaction"]
CAS --> TO["Target Stage + event"]
Review approval 绑定 Case version;内容变更后旧批准不能继续授权离开阶段。
13. Case Event 是流程账本¶
每次 add/update/transition/review/blocker/automation 都写 Case Event,包含 actor、payload、from/to、run 等。当前 Case row 是读模型,Event 解释历史。
它不是完全 event-sourced 重放架构:权威当前状态仍在 Case row;Event 用于审计、automation trigger 和 UI timeline。
14. Blocker 与子 Case¶
Case blocker 是独立 DAG,并有 no-self check/unique constraint。子 Case 用 parentCaseId + parent version 表达 breakdown。
Parent 保存 child count/terminal child count 以加速 rollup,但服务仍有 reconcile/验证路径,防计数漂移导致错误过 gate。
Breakdown stage 可以从一个 Case 创建多个子 Case,并定义 carry-over field policy,避免把敏感/不相关字段全部复制。
15. Case 与 Issue Link¶
Link role 包括:
- origin;
- conversation;
- work;
- automation。
为什么要 role?同一个 Case 可能:
- 由某 Issue 发起;
- 用另一 Issue 作为持续对话;
- 为当前 stage 创建工作 Issue;
- 自动化运行再创建执行 Issue。
服务选择“当前 conversation source”时要按 role、retired 状态和 run context 解析,不能只取最新 link。
16. Stage Automation¶
Stage 可绑定 Routine。进入 stage 后,系统:
- 固化 Routine revision;
- 从 Case fields 构造变量;
- 生成 context markdown/preamble;
- 创建 execution Issue;
- 保存 Case↔Issue automation link;
- 入队 Agent;
- 结果通过事件/回调更新 Case。
Pipeline 不直接调用模型,它复用 Routine + Issue + Heartbeat 执行栈。
17. Automation Ledger 与幂等¶
pipeline_automation_executions 用:
唯一标识一次 stage automation。它保存 routine、execution issue、status、retry-of、generation、error。
flowchart TD
EVT["Case event"] --> INS{"insert automation ledger"}
INS -->|unique conflict| OLD["already handled → idempotent"]
INS -->|created| RUN["create linked Issue + run"]
RUN --> OK{"outcome"}
OK -->|success| DONE["ledger succeeded"]
OK -->|failure| FAIL["ledger failed + retry plan"]
FAIL --> RETRY["new generation / retryOf"]
先写 ledger 再启动外部工作,可防事件重复交付创建多个 Agent 任务。
18. Retry 需要清理上一次影响¶
Pipeline automation retry 不能简单再跑:上次可能已创建子 Case、Issue link、文档或 pending suggestion。Service 会构造 retry plan:
- 哪些上次产物 retire;
- 哪些保留为证据;
- 新 generation;
- link/child/field 怎样重建;
- blocker/approval 是否需重新评估。
这是业务自动化比普通函数 retry 更复杂的地方。
19. Parent Rollup 与自动推进¶
当子 Case terminal:
- 更新 parent counts;
- 写 child terminal event;
- 检查期望子数量;
- 检查 blockers/review;
- 满足 gate 时可 auto-advance parent;
- 通知 linked work Issue 上游内容变化。
Rollup 仍使用 transaction/version,防多个子项同时完成让 parent 重复 transition。
20. Routine 与 Pipeline 的边界¶
| 需求 | 用 Routine | 用 Pipeline |
|---|---|---|
| 每周生成报告 | ✓ | 可能不需要 |
| 定时唤醒 Agent 做一项工作 | ✓ | |
| 一个业务项跨多阶段流转 | ✓ | |
| 每阶段有 form/review/blocker | ✓ | |
| 阶段进入时自动运行 Agent | Pipeline 调用 Routine | ✓ |
| 只需 Issue 状态流 | Issue workflow | 不要过度建 Pipeline |
21. 可复用经验¶
- Cron 只负责触发,Routine 要保存 revision、input、Issue 和 run 证据。
- 自动化工作仍走正常 Issue/Heartbeat,避免治理旁路。
- Pipeline Case 与工作 Issue 分开,通过带 role 的 link 协作。
- Lease 管临时 owner,version 管 optimistic concurrency。
- Review approval 要绑定内容 version,变更后自动失效。
- 先写 automation ledger,再产生外部副作用;唯一键对齐业务事件身份。
- Retry 要显式清理/retire 上一 generation 的业务影响。
源码入口¶
packages/db/src/schema/routines.tsserver/src/services/routines.tsserver/src/routes/routines.tspackages/db/src/schema/pipelines.tspackages/db/src/schema/pipeline_cases.tspackages/db/src/schema/pipeline_case_events.tsserver/src/services/pipelines.tsserver/src/services/pipeline-case-outputs.tsdocs/pipelines-tutorial.md
自动化最终仍需给人可审查的结果:18 · Documents、Artifacts 与 Work Products。