# 03-prompt-evolution.md — Prompt 进化：从固定步骤到自主决策

**日期**: 2026-05-30
**作者**: 庞统
**状态**: 已修订 v1.1（根据司马懿 2026-05-30 评审意见）
**前置**: `02-main-session-delegation.md`（#02 统一走 main session）
**来源**: architecture-v3.0.md §10.4 Prompt 进化

---

## 一、问题：现有 Prompt 是固定步骤指令，不 AI Native

### 现状

系统中有 **6 种 prompt 模板**，构建方式各不相同：

| 模板 | 位置 | 行为模式 | 问题 |
|------|------|---------|------|
| `SPAWN_PROMPT_TEMPLATE` | spawner.py L62 | 固定 4 步骤（标 working → 干活 → 写产出 → 标 review） | ❌ 不信任 Agent 自主能力，curl 硬编码，冗长 |
| `DISCUSSION_PROMPT_TEMPLATE` | spawner.py L148 | 开放式（你是自主的） | ✅ 方向正确，但与 SPAWN 模板风格断裂 |
| `CLAIM_PROMPT` | ticker.py `_build_claim_prompt` | 固定 4 步骤（读黑板 → claim → 标 working → 执行） | ❌ 没注入 Agent 身份/能力，庞统会抢张飞的活 |
| `REVIEW_PROMPT` | ticker.py `_build_review_prompt` | 三问框架 | ✅ 设计合理，小优化即可 |
| `MENTION_PROMPT` | ticker.py `_build_mention_prompt` | 固定步骤 | ❌ 过于机械 |
| `DELEGATE_PROMPT` | dispatcher.py `_build_delegate_prompt` | 列出团队成员让庞统选 | ✅ 可以保留 |

### 核心问题

1. **SPAWN_PROMPT 太长太死板**：~100 行，手把手教 curl，Agent 像执行脚本而非自主决策
2. **CLAIM_PROMPT 不注入身份**：广播时不告诉 Agent 自己擅长什么，导致争抢
3. **模板碎片化**：6 个模板散布在 3 个文件中，风格不统一
4. **curl 硬编码**：Agent 已经有工具（read/write/exec），不需要 curl
5. **不区分 Mail 路径 vs Task 路径**：Mail 模板已精简（inform/request），Task 模板还是老式

### v3.0 设计方向回顾（architecture-v3.0.md §10.4）

> 从"固定步骤指令"变成"身份 + 目标 + 能做什么 + 约束 + 交接责任"

```markdown
# 你的身份
你是 {agent_name}，{agent_role}。擅长 {agent_capabilities}。

# 你的任务
{task_title}: {task_description}
类型: {task_type} | 风险: {risk_level}
必要条件: {must_haves}

# 你能做什么
通过 API 操作黑板（{api_base}）:
- 读任何任务详情: GET /api/projects/{pid}/tasks/{id}?expand=all
- ...

# 约束
- 完成后必须写产出 + 标 review
- 安全红线: {guardrails_summary}
```

---

## 二、方案：统一 Prompt 架构

### 2.1 设计原则

1. **信任 Agent** — Agent 有 SOUL.md、workspace、工具能力，不需要手把手教
2. **身份先行** — 每个 prompt 开头注入 Agent 身份和能力，让 Agent 知道自己能干什么、不该干什么
3. **目标清晰** — 告诉 Agent 要做什么，不告诉怎么做
4. **约束为底线** — 红线是硬约束，其余让 Agent 自主
5. **Mail 不动** — Mail 模板（inform/request）已经在 v1.0 验证过，保持不变

### 2.2 Agent 能力画像注入

从 Router 的 AgentProfile 中提取，注入到 prompt：

```
你是 {agent_id}，{role}。
你的专长: {capabilities}
```

| Agent | capabilities 注入 |
|-------|-------------------|
| zhangfei-dev | 编码、实现、脚本 |
| simayi-challenger | 审查、质量检查、辩论 |
| guanyu-dev | 风控、合规、仓位检查 |
| zhaoyun-data | 数据获取、清洗、验证 |
| jiangwei-infra | 部署、基础设施、Docker、vnpy |
| pangtong-fujunshi | 规划、协调、策略、升级处理 |

### 2.3 统一 Prompt 结构

所有 Task 路径的 prompt 统一为三段式：

```
┌─────────────────────────────┐
│ 1. 身份段（固定）            │  Agent ID + 专长 + 角色
├─────────────────────────────┤
│ 2. 任务段（变化）            │  具体任务信息 + 上下文
├─────────────────────────────┤
│ 3. 约束段（固定）            │  红线 + 产出要求 + API 摘要
└─────────────────────────────┘
```

Mail 路径的 prompt 不变（inform/request 模板已精简）。

---

## 三、新模板设计

### 3.1 Task 执行模板（替代 SPAWN_PROMPT_TEMPLATE）

```markdown
你是 {agent_id}，专长: {capabilities}。

## 任务
{title}
{description}

项目: {project_id} | ID: {task_id}
类型: {task_type} | 优先级: {priority}
验收标准: {must_haves}

{retry_context}

## 你能做什么
- 读任务详情（含依赖、讨论、产出）: GET {api_base}/projects/{project_id}/tasks/{task_id}?expand=all
- 读所有活跃任务: GET {api_base}/projects/{project_id}/tasks?status=working,claimed,review
- 写产出: POST {api_base}/projects/{project_id}/tasks/{task_id}/outputs
- 写评论/交接: POST {api_base}/projects/{project_id}/tasks/{task_id}/comments
- 更新状态: POST {api_base}/projects/{project_id}/tasks/{task_id}/status
- 创建子任务: POST {api_base}/projects/{project_id}/tasks
- 认领任务: POST {api_base}/projects/{project_id}/tasks/{{id}}/claim

## 约束
- 完成后必须写产出物（output）并标 review，不能无产出就提交
- 失败了标 failed 并写明原因
- 产出物 handoff comment ≥ 50 字符（用于系统验证）
- 禁止使用 sessions_send 直接发消息（用 Mail API 或黑板 comment）
- 安全红线: {guardrails_summary}

### API 请求体示例
写产出: POST .../outputs
```json
{{"agent": "{agent_id}", "content_type": "code", "title": "产出标题", "content_path": "/path/to/file", "summary": "简要说明"}}
```

写评论: POST .../comments
```json
{{"author": "{agent_id}", "body": "评论内容（≥50字符）", "comment_type": "handoff"}}
```
```

**关键变化**：
- 删掉固定 4 步骤（标 working → 干活 → 写产出 → 标 review），让 Agent 自主决策
- 删掉 curl 硬编码，改为 API 端点列表（Agent 有工具能力）
- 加身份注入（capabilities）
- 加约束底线

### 3.2 广播认领模板（替代 _build_claim_prompt）

```markdown
你是 {agent_id}，专长: {capabilities}。

## 待认领任务
{task_list}

## 规则
- 只认领符合你专长的任务。你的专长是 {capabilities}，不适合的任务不要认领
- 不确定时不要认领，留给更合适的 Agent
- 认领后必须写产出物再转 review

## 你能做什么
- 读任务详情: GET {api_base}/projects/{project_id}/tasks?status=pending
- 认领: POST {api_base}/projects/{project_id}/tasks/{{TASK_ID}}/claim
  body: {{"agent": "{agent_id}"}}
- 认领后标 working: POST {api_base}/projects/{project_id}/tasks/{{TASK_ID}}/status
  body: {{"status": "working", "agent": "{agent_id}"}}
- 没有适合你的任务则 NO_REPLY

## 约束
- 一个 tick 只认领一个任务
- 禁止使用 sessions_send 直接发消息
```

**关键变化**：
- 加身份+专长注入，明确告诉 Agent "你的专长是 X，不适合的不要认领"
- 从"建议"变成"约束"
- 简化操作指引

### 3.3 @mention 模板（替代 _build_mention_prompt）

```markdown
你在黑板上被 @ 了。

## 你的身份
你是 {agent_id}，专长: {capabilities}。

## 相关讨论
{mentions_text}

## 任务上下文
- 项目: {project_id}
- 任务: {task.title}
- 描述: {task.description}

## 你能做什么
- 读完整上下文: GET {api_base}/projects/{project_id}/tasks/{task.id}?expand=all
- 回应: POST {api_base}/projects/{project_id}/tasks/{task.id}/comments
- 如果讨论收敛到可执行任务，可以创建 sub task

## 约束
- 只回应与你专长相关的内容
- 禁止使用 sessions_send 直接发消息
```

### 3.4 Review 模板（保留，小幅优化）

Review 模板已经合理（三问框架），只做两处优化：

1. 加身份注入："你是 pangtong-fujunshi，任务协调员。"
2. 删掉 curl 硬编码，改为 API 端点列表

### 3.5 Delegate 模板（保留）

`_build_delegate_prompt` 保留不变。它只给庞统用，且设计合理（列出团队成员让庞统选）。

### 3.6 Discussion 模板（保留）

`DISCUSSION_PROMPT_TEMPLATE` 方向正确（"你是自主的"），保留不变。

### 3.7 Mail 模板（不变）

Mail 路径的 inform/request 模板已在 v1.0 验证，保持不变。

---

## 四、能力注入机制

### 4.1 数据来源

从 Router 的 `AgentProfile.capabilities` 提取。Router 已在初始化时加载所有 Agent 画像：

```python
# router.py
self.agent_profiles = {
    "zhangfei-dev": AgentProfile(capabilities=["coding", "implementation", "scripting"], ...),
    "simayi-challenger": AgentProfile(capabilities=["review", "quality_check", "debate"], ...),
    ...
}
```

### 4.2 中文映射

Agent 需要中文的能力描述，不是英文标签：

```python
CAPABILITY_LABELS = {
    "coding": "编码",
    "implementation": "实现",
    "scripting": "脚本",
    "review": "审查",
    "quality_check": "质量检查",
    "debate": "辩论",
    "deploy": "部署",
    "infrastructure": "基础设施",
    "docker": "Docker",
    "vnpy": "vnpy框架",
    "risk": "风控",
    "compliance": "合规",
    "position_check": "仓位检查",
    "data": "数据",
    "acquisition": "获取",
    "cleaning": "清洗",
    "verification": "验证",
    "planning": "规划",
    "coordination": "协调",
    "escalation": "升级处理",
    "strategy": "策略",
}
```

### 4.3 注入位置

在 `spawner.py` 中新增方法 `_inject_agent_identity(agent_id)` → 返回身份段字符串。所有 prompt 构建方法调用此方法获取身份段。

---

## 五、兜底机制

### 5.1 无人认领兜底（已实现）

广播认领路径已有兜底：

```
_broadcast_claim():
  for task in pending:
    if retry_count >= 3:
      → escalated（升级庞统）
    else:
      → 广播给 idle agents
```

3 轮广播无人认领 → 任务标 `escalated` → 庞统接手（走 delegate 路径）。

### 5.2 Claim 并发保护（已实现）

`claim_task()` 是原子 CAS 操作：

```sql
UPDATE tasks SET status='claimed', assignee=? WHERE id=? AND status='pending'
```

多个 Agent 同时 claim 同一个任务，只有第一个成功（`rowcount=1`），其余返回 False。Agent 在 prompt 中被告知：「如果 claim 失败说明已被别人认领，NO_REPLY 退出」。

**不需要两步**（claim + working）。claim 成功即标 `claimed`，Agent 再标 `working` 时黑板校验 `status=claimed`，不存在竞态窗口。

---

## 六、占位符定义

### 6.1 `{guardrails_summary}`

**来源**: `GuardrailEngine.rules` 中的 6 条红线摘要。

**注入方式**: spawner 在构建 prompt 时从 `GuardrailEngine.rules` 提取 `rule_name`，拼接为逗号分隔的字符串。

```python
def _get_guardrails_summary(self) -> str:
    if not self.guardrails:
        return "无特殊限制"
    return "、".join(r["name"] for r in self.guardrails.rules[:6])
```

**当前 6 条红线**（PRD §10.1）：
1. 禁止操作生产环境数据库
2. 禁止执行未审核的外部代码
3. 禁止绕过风控规则
4. 禁止修改系统配置
5. 单次交易不得超过限额
6. 禁止未授权的资金操作

**没有 guardrails 时**: 填 "无特殊限制"。

### 6.2 `{retry_context}`

**来源**: `tasks.retry_count` 字段 + 上次执行的 outputs/comments。

**注入逻辑**（复用现有 `_build_retry_context`，增强）：

```python
def _build_retry_context(self, task) -> str:
    if (task.retry_count or 0) == 0:
        return ""
    parts = ["⚠️ 这是重试（第 {} 次尝试），之前的执行失败了。".format(task.retry_count + 1)]
    # 可选：注入上次失败原因（从 comments 中取 system 写的失败记录）
    return "\n".join(parts)
```

**首次执行时**: 填空字符串，不渲染重试段。

---

## 七、改动范围

| 文件 | 改动点 | 改动量 |
|------|--------|--------|
| `spawner.py` | 重写 `SPAWN_PROMPT_TEMPLATE`；新增 `_inject_agent_identity()`；修改 `_build_spawn_message()` | ~60 行 |
| `ticker.py` | 重写 `_build_claim_prompt()`；重写 `_build_mention_prompt()`；小改 `_build_review_prompt()` | ~50 行 |
| `dispatcher.py` | `_build_delegate_prompt()` 加身份注入 | ~5 行 |

**总改动量**: ~115 行，涉及 3 个文件。

### 不改的

- `MAIL_INFORM_TEMPLATE` / `MAIL_REQUEST_TEMPLATE` — 已精简，不变
- `DISCUSSION_PROMPT_TEMPLATE` — 方向正确，不变
- `router.py` — 只读 capabilities，不改
- `prompt_templates/` 目录 — 暂不创建（模板代码量小，直接在 Python 中管理更方便调试）

---

## 八、收益

| 维度 | 改善 |
|------|------|
| **Token 节省** | SPAWN_PROMPT 从 ~100 行 → ~30 行，每次 spawn 节省 ~70 行 |
| **Agent 自主性** | 从"固定步骤"到"目标+约束"，Agent 自主决策执行路径 |
| **争抢问题** | 身份+专长注入，Agent 明确知道"我不该认领这个" |
| **风格统一** | 6 个模板统一为三段式结构 |
| **curl 消除** | 不再硬编码 curl，Agent 用自己的工具能力 |

---

## 九、风险

| 风险 | 缓解 |
|------|------|
| **Agent 过度自主** | 约束段保留硬性底线（必须写产出、必须标 review） |
| **身份注入不够强** | 用"只认领符合你专长的任务"而非"建议" |
| **API 端点不熟悉** | 每个模板都列出完整 API 列表，Agent 不需要猜 |
| **Review 模板改坏** | Review 只做小改（加身份+去 curl），不动三问框架 |

---

## 十、实施计划

### Phase 1：Task 执行模板 + 身份注入

1. 新增 `_inject_agent_identity()` 到 spawner.py
2. 重写 `SPAWN_PROMPT_TEMPLATE`
3. 重写 `_build_claim_prompt()`
4. 部署 + 单任务 E2E 验证

### Phase 2：其他模板统一

1. 重写 `_build_mention_prompt()`
2. 小改 `_build_review_prompt()`
3. `_build_delegate_prompt()` 加身份注入
4. 全量 E2E 验证
