AI AutoDev Team — 产品 从开始到落地的构想

0 阅读42分钟

AI AutoDev Team — 产品需求文档 (PRD) v2.1

哲学: 不下发剧本,只下发任务。不硬编码流程,只定义边界。不预设角色,只约束行为。 版本: v2.1 日期: 2026-05-09 状态: 增量修订(基于 v2.0 评估反馈) 修订内容: 新增 Phase 0、执行环境规范、LLM 调用策略、任务复杂度分类器、错误分类规范;简化 Stigmergy;修正 Phase 1 交付物;补充验证类型;调整价值主张


1. 产品哲学:从"编排"到"蜂群"

1.1 核心理念

旧思维(已抛弃):

  • ❌ 预定义 5 个角色(PO/TL/Dev/QA/Ops),每个有固定剧本
  • ❌ 固定状态机(需求→设计→开发→测试→部署)
  • ❌ Agent 像提线木偶,只能做编排者预设的动作

蜂群思维:

  • 只下发目标:"实现用户注册模块,含邮箱验证"
  • 只规定边界:"用 TypeScript + Next.js,测试覆盖≥80%,不碰生产数据库"
  • 只约束输出:"交付可运行的代码 + 测试 + 文档"
  • 蜂群并行攻击:不是 1 个 Agent 串行,而是 N 个 Agent 同时从多角度拆解、搜索、编码、验证
  • 去中心化涌现:没有总指挥,Agent 根据局部信息自主决策,群体涌现最优解

1.2 蜂群 vs 单兵:效率对比(v2.1 修订)

单 Agent蜂群 (Swarm)提速比
信息收集1 人搜索 10 个链接3 人同时搜索不同关键词1.5-2x
技术选型1 人对比 5 个库,纠结 20 分钟3 人各自深入 1 个库,交叉验证2-3x
代码实现1 人串行写多文件3 人同时写不同模块1.5-2x
Bug 修复1 人反复试错2 人双路排查,取先成功1.5-2.5x
验证1 人跑测试,失败再修1 人跑测试,1 人同步写边界测试1.2-1.5x

关键洞察:蜂群提速是有条件的——任务需要可并行化足够复杂。简单任务(解析 CSV、单文件修改)蜂群开销大于收益。蜂群适合技术选型调研复杂 Bug 排查,不适合简单重复任务。

1.3 系统定义

AI AutoDev Team (AAT) v2 + Swarm 是一个自组织蜂群软件开发系统

  1. 人类输入:任务描述 + 边界约束 + 验收标准
  2. 系统输出:可运行的代码产物 + 执行日志 + 验证报告
  3. 过程黑盒:一群 Agent 像蜂群一样围绕任务并行工作、局部通信、涌现结果

2. 系统总览:极简输入 → 蜂群并行 → 可验证输出

2.1 架构极简图

┌─────────────────────────────────────────────────────────────────┐
│                        HUMAN INPUT                              │
│  ┌──────────────────────────────────────────────────────────┐  │
│  │  "实现一个支持邮箱验证码的用户注册模块"                     │  │
│  │  约束: {tech: "Next.js+Prisma", cost_limit: "$5", ...}   │  │
│  └──────────────────────────────────────────────────────────┘  │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│                    MISSION DECOMPOSITION                        │
│  AI 蜂群同时多角度拆解:                                        │
│  Agent-A: "拆成前端+后端+数据库"                               │
│  Agent-B: "拆成 API+UI+验证+测试"                              │
│  Agent-C: "拆成安全+性能+功能"                                 │
│  → 汇总取并集,生成最优任务树                                  │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│                    SWARM EXECUTION                              │
│                                                                 │
│    ┌─────────┐  ┌─────────┐  ┌─────────┐  ┌─────────┐        │
│    │Agent-1  │  │Agent-2  │  │Agent-3  │  │Agent-N  │        │
│    │搜索Resend│  │搜索SendGrid│  │搜索AWS SES│  │写Schema │        │
│    │并发调研  │  │并发调研  │  │并发调研  │  │并发编码  │        │
│    └────┬────┘  └────┬────┘  └────┬────┘  └────┬────┘        │
│         │            │            │            │              │
│         └────────────┴────────────┴────────────┘              │
│                           │                                    │
│                    ┌──────┴──────┐                            │
│                    │ Swarm Mesh  │ ← 局部通信、结果汇聚        │
│                    │  (去中心化)  │                             │
│                    └──────┬──────┘                            │
│                           │                                    │
│         ┌─────────────────┼─────────────────┐               │
│         ▼                 ▼                 ▼               │
│    ┌─────────┐      ┌─────────┐      ┌─────────┐          │
│    │Agent-X  │      │Agent-Y  │      │Agent-Z  │          │
│    │集成邮箱 │      │写API    │      │写前端   │          │
│    │服务     │      │端点     │      │页面     │          │
│    │(用最优) │      │(等Schema)│      │(等API)  │          │
│    └─────────┘      └─────────┘      └─────────┘          │
│                                                                 │
│  ┌────────────────────────────────────────────────────────┐  │
│  │              TOOL MESH (工具自治层)                      │  │
│  └────────────────────────────────────────────────────────┘  │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│                    VERIFICATION LAYER                           │
│  每个子任务必须有可验证的交付物,不通过 → 蜂群自动修复          │
│  [API测试通过✓] [Schema验证✓] [覆盖率82%✓] [E2E通过✓]          │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│                        HUMAN OUTPUT                             │
│  ┌──────────────────────────────────────────────────────────┐  │
│  │  ✅ 代码仓库 (Git 分支)                                    │  │
│  │  ✅ 测试报告 (自动运行结果)                                 │  │
│  │  ✅ ADR: 蜂群共识选 Resend (3人调研交叉验证)               │  │
│  │  ✅ 成本报告 ($3.2 / $5.0, 蜂群并行节省 60% 时间)           │  │
│  └──────────────────────────────────────────────────────────┘  │
└─────────────────────────────────────────────────────────────────┘

2.2 唯一硬编码的东西

层级硬编码内容理由
输入协议任务描述格式 + 约束 Schema人类和系统必须能对话
验证框架什么是"通过"的客观标准避免AI自我欺骗
安全边界不能删的文件、不能调的API、预算上限防止破坏
工具网关MCP/Skill 的标准调用协议统一接口

除此之外,一切自治。


3. 任务系统:Mission → Verification Tree

3.1 任务分解引擎(自主拆解)

class MissionDecomposer:
    """
    把人类的大需求,拆解成可验证的子任务树。
    不依赖预设模板,完全由 AI 根据任务语义自主拆解。
    """
    
    async def decompose(self, mission: Mission) -> TaskTree:
        """
        输入: "实现用户注册模块,含邮箱验证"
        
        输出(示例,实际由 AI 自主决定):
        
        TaskTree {
            root: "实现用户注册模块",
            children: [
                Task {
                    id: "T1",
                    description: "设计数据库用户表 Schema",
                    deliverable: "prisma/schema.prisma 中含 User 模型",
                    verification: "prisma validate 通过",
                    dependencies: [],
                    estimated_cost: "$0.3"
                },
                Task {
                    id: "T2", 
                    description: "实现 /api/auth/register 端点",
                    deliverable: "app/api/auth/register/route.ts",
                    verification: "curl 请求返回 200,数据库有记录",
                    dependencies: ["T1"],
                    estimated_cost: "$0.5"
                },
                Task {
                    id: "T3",
                    description: "集成邮箱验证码服务",
                    deliverable: "可发送验证码邮件",
                    verification: "测试邮箱收到邮件,验证码可验证",
                    dependencies: [],
                    # AI 自主决定: 搜索对比 SendGrid/Resend/AWS SES,选性价比最高的
                    tool_search_hint: "email verification service"
                },
                Task {
                    id: "T4",
                    description: "前端注册页面",
                    deliverable: "app/register/page.tsx",
                    verification: "Playwright 测试通过",
                    dependencies: ["T2", "T3"]
                },
                Task {
                    id: "T5",
                    description: "单元测试 + 集成测试",
                    deliverable: "测试文件 + coverage 报告",
                    verification: "npm test 通过 && coverage≥80%",
                    dependencies: ["T2", "T3", "T4"]
                }
            ]
        }
        """
        
        # 让 LLM 自主思考如何拆解,只约束输出格式
        prompt = f"""
        你是一个经验丰富的技术负责人。
        
        任务: {mission.description}
        约束: {json.dumps(mission.constraints)}
        验收标准: {json.dumps(mission.acceptance_criteria)}
        
        请把任务拆解为可独立执行的子任务树。
        每个子任务必须包含:
        1. 具体做什么(一句话)
        2. 交付物是什么(文件路径或运行结果)
        3. 怎么验证通过(可执行的具体命令或检查)
        4. 依赖哪些前置任务
        
        不要套用模板,根据任务实际性质决定粒度。
        有的任务需要拆很细(如复杂算法),有的可以很粗(如简单配置)。
        """
        
        return await llm.generate_structured(prompt, schema=TaskTree)

3.2 子任务必须可验证

@dataclass
class Task:
    id: str
    description: str
    
    # === 交付物定义(必须具体)===
    deliverable: str  # "app/api/auth/register/route.ts 文件存在且可运行"
    
    # === 验证器(必须可自动执行)===
    verification: VerificationSpec
    
    # === 依赖(其他子任务)===
    dependencies: List[str] = field(default_factory=list)
    
    # === 资源预估(AI 自主估算)===
    estimated_cost: Optional[str] = None  # "$0.5"
    estimated_time: Optional[int] = None  # 分钟

@dataclass
class VerificationSpec:
    """
    验证必须客观、自动、无歧义。
    """
    type: str  # "file_exists", "command_exit_0", "coverage_threshold", "curl_200", "e2e_pass"
    command: Optional[str]  # "npm test -- --coverage"
    expected: str  # "coverage: 80%"
    timeout_seconds: int = 120

验证示例:

子任务验证方式
"创建数据库表"prisma migrate dev 执行成功,且 prisma db pull 能看到新表
"API 可用"curl -X POST http://localhost:3000/api/register 返回 {"success": true}
"测试覆盖"npx jest --coverage --coverageReporters=text-summary 输出含 Lines: 82%
"前端可访问"npx playwright test tests/register.spec.ts 退出码 0
"文档完整"grep -c "## API Reference" docs/README.md ≥ 1

5. 蜂群协调层:Swarm Coordination

5.1 蜂群核心机制

蜂群不是"多线程 Agent",而是去中心化、自组织、涌现式的群体智能系统。

机制 1: 去中心化任务队列 (Decentralized Task Queue)

没有中央调度器分配任务。Agent 自己"嗅探"任务、自主认领。

class DecentralizedTaskBoard:
    """
    蜂群任务板——像蜜蜂发现蜜源后跳八字舞通知同伴
    """
    
    def __init__(self):
        # 任务板是共享的,但没有"分配者"
        self.tasks = {}  # task_id -> Task
        self.claims = {}  # task_id -> agent_id (谁先抢到谁做)
        self.progress = {}  # task_id -> 0.0-1.0
        
    async def post_task(self, task: Task):
        """任务发布到板上(由 Decomposer 或 Agent 产生)"""
        self.tasks[task.id] = task
        # 发布事件,所有 Agent 都能感知
        await self.emit(TaskPostedEvent(task))
    
    async def claim_task(self, agent: Agent, task_id: str) -> bool:
        """Agent 自主认领任务"""
        if task_id in self.claims:
            return False  # 已被认领
        
        # Agent 自己判断:我能做这个任务吗?
        task = self.tasks[task_id]
        confidence = await agent.assess_capability(task)
        
        if confidence < 0.5:
            return False  # Agent 自认能力不足,不抢
        
        self.claims[task_id] = agent.id
        agent.current_task = task
        return True
    
    async def abandoned_task(self, agent: Agent, task_id: str, reason: str):
        """Agent 放弃任务(如遇到困难),其他人可以重新认领"""
        if self.claims.get(task_id) == agent.id:
            del self.claims[task_id]
            # 广播:这个任务又空了,谁能做?
            await self.emit(TaskAbandonedEvent(task_id, reason))
机制 2: 冗余并行 (Redundant Parallelism)

同一任务多个 Agent 同时尝试,取最优结果。

class RedundantExecution:
    """
    关键任务同时派 N 个 Agent 做,取最快/最好的结果
    """
    
    async def execute_with_redundancy(self, task: Task, n: int = 2) -> TaskResult:
        """
        同时启动 2-3 个 Agent 做同一个任务
        """
        # 启动 N 个 Agent
        agents = [self.spawn_agent() for _ in range(n)]
        
        # 同时执行
        futures = [agent.execute(task) for agent in agents]
        
        # 谁先完成就先验证
        done, pending = await asyncio.wait(
            futures, 
            return_when=asyncio.FIRST_COMPLETED
        )
        
        # 先完成的先验证
        for future in done:
            result = await future
            if await self.verify(result, task):
                # 成功!取消其他 Agent
                for p in pending:
                    p.cancel()
                return result
        
        # 第一个验证失败,等第二个
        if pending:
            done2, _ = await asyncio.wait(pending, return_when=asyncio.FIRST_COMPLETED)
            for future in done2:
                result = await future
                if await self.verify(result, task):
                    return result
        
        # 全部失败,合并错误信息交给蜂群诊断
        errors = [f.exception() for f in futures if f.exception()]
        return await self.swarm_diagnose(task, errors)

适用场景:

任务类型并行度理由
技术选型调研3不同 Agent 各深入 1 个方案,交叉验证
Bug 修复2同时尝试不同修复策略
架构设计2同时产出 2 个方案,对比取优
单元测试1确定性高,无需冗余
复杂算法实现2不同实现思路,跑 benchmark 选优
机制 3: 局部通信 (Local Communication)

Agent 不和所有人通信,只和"邻居"通信(减少信息噪音)。

class LocalCommunicationMesh:
    """
    Agent 只和相关的 Agent 通信,不是全连接广播
    """
    
    def get_neighbors(self, agent: Agent, context: SwarmContext) -> List[Agent]:
        """
        邻居定义(动态变化):
        1. 做同一个父任务的 Agent
        2. 当前任务的上下游依赖 Agent
        3. 使用相同技术栈的 Agent(可以分享工具使用经验)
        """
        neighbors = set()
        
        # 同任务组的 Agent
        if agent.current_task:
            neighbors.update(
                a for a in context.agents 
                if a.current_task and a.current_task.parent_id == agent.current_task.parent_id
            )
        
        # 依赖关系的 Agent
        for dep_id in agent.current_task.dependencies:
            dep_agent = context.find_agent_by_task(dep_id)
            if dep_agent:
                neighbors.add(dep_agent)
        
        return list(neighbors)
    
    async def whisper(self, from_agent: Agent, message: SwarmMessage):
        """向邻居发送信息"""
        neighbors = self.get_neighbors(from_agent, self.context)
        
        for neighbor in neighbors:
            await neighbor.inbox.put(message)
            
            # 如果信息特别重要(如发现了一个好用的工具),标记为"强烈推荐"
            if message.priority == "discovery":
                # 邻居可能会继续传播给它的邻居(信息扩散)
                await self._gossip(neighbor, message, ttl=3)
机制 4: 痕迹标记 (Stigmergy) — 简化版

v2.1 变更:移除痕迹衰减机制,改为简单 key-value 记录。衰减机制复杂度高但实际价值有限。

像蚂蚁用信息素标记路径,Agent 用"数字痕迹"标记环境。

class StigmergyEnvironment:
    """
    数字痕迹系统——Agent 在环境中留下标记,影响其他 Agent 的行为。
    简化版:简单的 key-value 存储,无衰减。
    """

    def __init__(self):
        self.trails = {}  # location -> StigmergyMark

    async def mark(self, agent: Agent, location: str, mark_type: str, content: str):
        """Agent 在环境中留下痕迹"""
        self.trails[location] = {
            "agent_id": agent.id,
            "location": location,
            "type": mark_type,  # "good_path" / "bad_path" / "tip"
            "content": content,
            "timestamp": datetime.utcnow().isoformat(),
        }

    async def sniff(self, location: str) -> Optional[dict]:
        """Agent 感知环境中的痕迹"""
        return self.trails.get(location)

    async def list_all(self, mark_type: str = None) -> List[dict]:
        """获取所有痕迹,可按类型过滤"""
        if mark_type:
            return [t for t in self.trails.values() if t["type"] == mark_type]
        return list(self.trails.values())

简化原因:

  • 痕迹衰减(0.9^hour)在实践中价值有限,任务重复率低
  • 简单 key-value 更易实现和维护
  • 如果后续发现简单版本不够用,可以再增加衰减机制

痕迹类型:

痕迹类型含义Agent 行为影响
good_path"这条路走得通"倾向于跟随
bad_path"这里有大坑"避开
tip"用 X 工具效率翻倍"优先尝试

场景示例:

  • Agent-1 尝试 SendGrid 失败,留下 bad_path(SendGrid 配置复杂)
  • Agent-2 嗅到痕迹,改试 Resend 成功,留下 tip(Resend 只需一行代码)
  • Agent-3 直接选 Resend
机制 5: 涌现共识 (Emergent Consensus)

没有投票机制,共识通过群体行为自然涌现。

class EmergentConsensus:
    """
    群体共识——不是投票,而是看大多数人怎么做
    """
    
    async def converge(self, swarm: Swarm, decision: str) -> Consensus:
        """
        例如:选哪个邮件服务?
        """
        # 收集所有 Agent 的"倾向"(不是投票,是观察它们实际选什么)
        tendencies = {}
        
        for agent in swarm.agents:
            if agent.current_task and "email" in agent.current_task.description.lower():
                # 看 Agent 实际在代码里引入了什么包
                choice = agent.detect_imported_package()
                tendencies[choice] = tendencies.get(choice, 0) + 1
        
        # 涌现结果:大多数人实际走的路
        if tendencies:
            winner = max(tendencies, key=tendencies.get)
            confidence = tendencies[winner] / sum(tendencies.values())
            
            return Consensus(
                choice=winner,
                confidence=confidence,
                basis="emergent_behavior",  # 基于实际行为,不是投票
                dissent= [c for c in tendencies if c != winner]  # 少数派选择
            )

5.2 蜂群动态拓扑

蜂群的组织结构不是固定的,根据任务动态变化。

class DynamicSwarmTopology:
    """
    蜂群根据任务类型自动调整组织结构
    """
    
    async def form_swarm(self, mission: Mission) -> Swarm:
        """根据任务性质决定蜂群形态"""
        
        # 任务分类
        if mission.is_exploratory():  # 探索性任务(如技术选型)
            return await self._form_scout_swarm(mission, size=5)
            # 5 个 Agent 分散探索不同方向
            
        elif mission.is_complex_feature():  # 复杂功能开发
            return await self._form_pipeline_swarm(mission, size=3)
            # 3 个 Agent 流水线:1 架构 + 2 编码(并行不同模块)
            
        elif mission.is_bug_fix():  # Bug 修复
            return await self._form_striker_swarm(mission, size=2)
            # 2 个 Agent 同时尝试不同修复方案
            
        elif mission.is_refactoring():  # 重构
            return await self._form_guardian_swarm(mission, size=2)
            # 1 个重构 + 1 个实时验证
    
    async def _form_scout_swarm(self, mission, size: int) -> Swarm:
        """
        侦察蜂群:分散探索,定期归巢汇报
        """
        agents = [self.spawn_agent() for _ in range(size)]
        
        # 给每个 Agent 分配不同的探索方向
        directions = self._diversify_directions(mission, n=size)
        for agent, direction in zip(agents, directions):
            agent.assign_direction(direction)
        
        # 定期归巢(同步点)
        swarm = Swarm(agents=agents, sync_interval=300)  # 每 5 分钟同步一次
        return swarm

5.3 蜂群执行协议

class SwarmExecutionProtocol:
    """
    蜂群执行主循环
    """
    
    async def run(self, swarm: Swarm, mission: Mission):
        # 1. 蜂群同时多角度拆解任务
        decompositions = await asyncio.gather(*[
            agent.decompose(mission) for agent in swarm.agents[:3]
        ])
        # 合并去重,生成最优任务树
        task_tree = self._merge_decompositions(decompositions)
        
        # 2. 发布到去中心化任务板
        for task in task_tree.tasks:
            await self.task_board.post_task(task)
        
        # 3. 蜂群自主认领 + 执行
        while not self.all_tasks_done(task_tree):
            # 每个空闲 Agent 自己嗅探任务板,抢任务
            idle_agents = [a for a in swarm.agents if a.is_idle()]
            
            await asyncio.gather(*[
                self._agent_work_loop(agent) for agent in idle_agents
            ])
            
            # 定期同步(归巢)
            await asyncio.sleep(10)
            await self._swarm_sync(swarm)
    
    async def _agent_work_loop(self, agent: Agent):
        """单个 Agent 的自治工作循环"""
        while True:
            # 1. 感知环境(嗅探痕迹)
            env_context = await self.stigmergy.sniff_surroundings(agent)
            
            # 2. 发现可认领的任务
            available = self.task_board.get_unclaimed()
            
            # 3. 自主评估哪个任务适合我
            candidates = [
                (task, await agent.assess_fit(task, env_context))
                for task in available
            ]
            candidates.sort(key=lambda x: x[1], reverse=True)
            
            # 4. 尝试认领最适合的
            for task, score in candidates:
                if score < 0.4:
                    break  # 没有适合我的任务,休息
                
                if await self.task_board.claim_task(agent, task.id):
                    # 5. 执行
                    result = await agent.execute(task)
                    
                    # 6. 验证
                    if await self.verify(result, task):
                        await self.task_board.complete_task(task.id, result)
                        # 留下 good_path 痕迹
                        await self.stigmergy.mark(agent, StigmergyMark(
                            location=task.id, type="good_path", strength=0.8
                        ))
                    else:
                        # 留下 caution 痕迹
                        await self.stigmergy.mark(agent, StigmergyMark(
                            location=task.id, type="caution", 
                            content=str(result.error), strength=0.6
                        ))
                        # 放弃任务,让其他 Agent 尝试
                        await self.task_board.abandoned_task(agent, task.id, str(result.error))
                    
                    break  # 做完一个,重新评估
            
            # 7. 如果没有可做的,等一会儿再嗅探
            await asyncio.sleep(5)

5.4 蜂群 vs 单 Agent 效率对比(v2.1 修订)

修订:下调提速比预期,增加适用场景说明。

场景单 Agent蜂群 (3 Agent)提速比适用条件
技术选型调研30 分钟串行10 分钟并行 + 5 分钟交叉2-3x需调研 3+ 方案
多模块功能开发2 小时串行50 分钟并行 + 10 分钟集成1.8-2.2x模块可并行
Bug 修复 (未知原因)1 小时试错20 分钟双路 + 自动对比1.5-2.5x失败原因未知
复杂重构3 小时1.5 小时并行重构 + 实时验证~2x有实时验证
文档编写20 分钟12 分钟分块并行~1.5x文档可分块
简单脚本/CURD5 分钟8 分钟(蜂群开销更大)< 1x不建议用蜂群

成本权衡:蜂群用 1.5-2x 的 API 费用,换 1.5-2.5x 的时间节省。仅适用于可并行化的复杂任务。简单任务退化为单 Agent。


6. Agent 执行环境规范 (新增)

本章定义 Agent 的运行环境,是 Phase 0 的核心交付物。没有稳定的执行环境,Agent 自治是空谈。

6.1 沙盒隔离级别

@dataclass
class SandboxConfig:
    """
    Agent 运行环境配置,分为三个隔离级别。
    """
    level: str  # "minimal" / "standard" / "relaxed"

    # 文件系统权限
    read_paths: List[str]  # 允许读取的路径
    write_paths: List[str]  # 允许写入的路径
    forbidden_paths: List[str]  # 禁止访问的路径 (即使在 read_paths 中)

    # 网络访问
    allowed_domains: List[str]  # 允许访问的域名白名单
    max_request_size_mb: int = 10

    # 命令执行
    allowed_commands: List[str]  # 允许执行的系统命令
    shell_enabled: bool = False

    # 资源限制
    max_memory_mb: int = 1024
    max_cpu_percent: int = 80
    max_execution_seconds: int = 300  # 单次任务超时

隔离级别定义:

级别适用场景特点
minimal验证/测试任务只读 + 无网络 + 无 shell
standard普通开发任务读写项目目录 + 允许的域名 + 有限命令
relaxed复杂调试任务读写HOME + 全网络 + shell 权限

6.2 工具接口定义

所有 Agent 工具必须通过 Tool Gateway 调用,禁止直接执行系统命令。

class ToolGateway:
    """
    工具网关:统一管理 Agent 可用的所有工具。
    每个工具必须有明确的输入/输出定义和错误处理。
    """

    async def execute(self, tool: ToolCall) -> ToolResult:
        """
        统一入口,返回结构化结果。
        失败时返回 ToolResult(error=...) 而非抛出异常。
        """

    def available_tools(self) -> List[ToolSpec]:
        """
        返回当前可用的工具列表及调用方式。
        Agent 通过此接口自主选择工具。
        """

# 工具分类
class FileSystemTools:
    """文件系统工具"""
    read_file(path: str) -> str
    write_file(path: str, content: str) -> bool
    list_dir(path: str) -> List[str]
    exists(path: str) -> bool

class CommandTools:
    """命令执行工具"""
    run_shell(command: str, timeout: int = 60) -> CommandResult
    run_script(script_path: str, args: List[str]) -> CommandResult

class SearchTools:
    """搜索工具"""
    web_search(query: str) -> List[SearchResult]
    code_search(query: str, repo: str) -> List[CodeResult]
    knowledge_base_search(query: str) -> List[KBResult]

class HttpTools:
    """HTTP 工具"""
    http_get(url: str) -> HttpResult
    http_post(url: str, body: dict) -> HttpResult

class DatabaseTools:
    """数据库工具"""
    db_query(sql: str) -> QueryResult
    db_execute(sql: str) -> ExecutionResult

6.3 工具调用失败处理

工具调用必须返回结构化结果,不能依赖异常来处理业务错误。

@dataclass
class ToolResult:
    success: bool
    data: Any = None
    error: Optional[str] = None
    error_code: str = "TOOL_ERROR"  # 错误分类代码
    retryable: bool = False  # 是否可重试
    cost_usd: float = 0.0

    @staticmethod
    def ok(data: Any, cost: float = 0.0) -> "ToolResult":
        return ToolResult(success=True, data=data, cost_usd=cost)

    @staticmethod
    def fail(error: str, code: str, retryable: bool = False, cost: float = 0.0) -> "ToolResult":
        return ToolResult(success=False, error=error, error_code=code, retryable=retryable, cost_usd=cost)

错误码分类:

错误码含义是否可重试
TOOL_NOT_FOUND工具不存在
TOOL_EXECUTION_FAILED工具执行失败视情况
SANDBOX_PERMISSION_DENIED权限不足
NETWORK_TIMEOUT网络超时
RESOURCE_EXCEEDED资源超限
INVALID_INPUT输入参数错误

6.4 执行引擎架构

class AgentExecutor:
    """
    Agent 执行引擎:管理单个 Agent 的生命周期。
    """

    async def execute_task(self, task: Task, context: ExecutionContext) -> TaskResult:
        """
        标准执行流程:
        1. 创建/获取沙盒
        2. 加载任务上下文
        3. 执行 Agent 逻辑循环
        4. 验证结果
        5. 清理沙盒
        """

        sandbox = await self.sandbox_manager.get_or_create(
            task_id=task.id,
            config=context.sandbox_config
        )

        try:
            # 加载约束到沙盒环境变量
            await sandbox.set_env("CONSTRAINTS", json.dumps(context.constraints))

            # Agent 执行循环
            agent = Agent(id=context.agent_id)
            state = AgentState.INITIAL

            while state != AgentState.DONE:
                state = await self._tick(agent, task, sandbox)

                # 超时检查
                if context.elapsed_seconds > task.max_execution_seconds:
                    return TaskResult.error("TIMEOUT", f"任务执行超过 {task.max_execution_seconds} 秒")

                # 资源检查
                if sandbox.exceeded_resource_limits():
                    return TaskResult.error("RESOURCE_EXCEEDED", "沙盒资源超限")

            # 验证
            return await self._verify_and_return(task, sandbox)

        finally:
            await sandbox.release()  # 释放沙盒,归还池中

    async def _tick(self, agent: Agent, task: Task, sandbox: Sandbox) -> AgentState:
        """
        Agent 执行循环的单次迭代。
        """
        # 1. Agent 思考下一步
        action = await agent.think(context=sandbox.current_state)

        # 2. 通过网关执行工具
        result = await self.tool_gateway.execute(action)

        # 3. 更新状态
        sandbox.update_state(result)

        # 4. 检查是否完成
        if result.is_terminal():
            return AgentState.DONE

        return AgentState.RUNNING

6.5 状态持久化

Agent 重启后能从断点恢复,不丢失任务进度。

@dataclass
class ExecutionSnapshot:
    """执行快照:记录 Agent 执行过程中的关键状态"""
    task_id: str
    agent_id: str
    state: AgentState
    current_step: int
    sandbox_path: str  # 沙盒工作目录路径
    tool_call_history: List[ToolCall]
    created_at: datetime
    updated_at: datetime

class SnapshotManager:
    """快照管理器:定期保存/恢复执行状态"""

    async def save(self, snapshot: ExecutionSnapshot):
        """保存执行快照到数据库"""

    async def restore(self, task_id: str) -> Optional[ExecutionSnapshot]:
        """根据 task_id 恢复执行快照"""

    async def checkpoint(self, task_id: str):
        """
        检查点:保存当前状态,返回恢复点 ID。
        用于 Agent 超时后重新拾取任务。
        """

恢复流程:

  1. 根据 task_id 查询最新 ExecutionSnapshot
  2. 重新创建沙盒,加载 sandbox_path 中的文件
  3. current_step 继续执行
  4. 重新执行最后一条 ToolCall(确保幂等性)

7. 自治执行层:Agent 自治协议

4.1 Agent 不是角色,是执行单元

@dataclass
class Agent:
    """
    Agent 是通用执行单元,不是预定义角色。
    每个 Agent 根据当前任务自主决定:
    - 用什么工具
    - 查什么资料
    - 怎么做最好
    """
    
    id: str
    current_task: Optional[Task] = None
    
    # Agent 的"能力"是动态的,不是预设的
    capabilities: Dict[str, float] = field(default_factory=dict)  # {"react": 0.8, "sql": 0.6}
    
    # Agent 的"记忆"是累积的,不是清空的
    experience: List[Experience] = field(default_factory=list)

class AgentAutonomyProtocol:
    """
    Agent 自治协议: 只给约束,不给剧本。
    """
    
    async def execute(self, agent: Agent, task: Task) -> TaskResult:
        # === Step 1: 理解任务 ===
        understanding = await self._comprehend(task)
        
        # === Step 2: 自主搜索信息 ===
        # Agent 自己决定需要什么信息
        knowledge_gaps = await self._identify_gaps(understanding)
        
        for gap in knowledge_gaps:
            info = await self._search(gap)
            understanding = self._assimilate(understanding, info)
        
        # === Step 3: 自主选工具 ===
        # Agent 自己决定用什么工具完成
        tools = await self._select_tools(task, understanding)
        
        # === Step 4: 自主执行 ===
        result = await self._execute_with_tools(task, tools)
        
        # === Step 5: 自我验证 ===
        verified = await self._verify(result, task.verification)
        
        if not verified:
            # 自主诊断问题
            diagnosis = await self._diagnose(result, task)
            # 自主决定修复策略
            fix_strategy = await self._decide_fix(diagnosis)
            result = await self._execute_fix(fix_strategy)
        
        return result

4.2 自主搜索能力

class AutonomousSearch:
    """
    Agent 自主搜索所需信息,不是人类喂给它。
    """
    
    async def search_for_task(self, task: Task) -> Knowledge:
        """
        Agent 自己判断需要什么信息。
        """
        
        # 让 LLM 决定搜索策略
        search_plan = await llm.generate(f"""
        任务: {task.description}
        
        你需要完成这个任务。但你现在什么都不知道。
        请列出你需要搜索了解的信息清单,按优先级排序。
        
        例如:
        - "Next.js 14 App Router 的 API route 怎么写"
        - "Prisma 的 email 字段怎么加唯一索引"
        - "Resend API 的发邮件示例代码"
        """")
        
        results = {}
        for query in search_plan.queries:
            # 多源并行搜索
            results[query] = await self._multi_source_search(query)
        
        return self._synthesize(results)
    
    async def _multi_source_search(self, query: str) -> SearchResults:
        """多源搜索,不限定来源"""
        
        sources = await asyncio.gather(
            # 搜索代码仓库历史
            self._search_codebase(query),
            
            # 搜索本地知识库
            self._search_knowledge_base(query),
            
            # 搜索网络 (如果有 web search tool)
            self._search_web(query),
            
            # 搜索已安装的包文档
            self._search_package_docs(query),
            
            # 搜索 MCP/Skill 可用工具
            self._search_mcp_registry(query),
        )
        
        return self._rank_by_relevance(sources)

4.3 自主工具选择

class AutonomousToolSelection:
    """
    Agent 根据任务自主选择和组合工具。
    不依赖预设的工具列表。
    """
    
    async def select_tools(self, task: Task, context: Knowledge) -> ToolChain:
        """
        Agent 自主决定用什么工具链。
        """
        
        # 发现可用工具
        available = await self.discovery.scan()
        
        # LLM 自主决策
        tool_chain = await llm.generate_structured(f"""
        任务: {task.description}
        你已了解的信息: {context.summary}
        
        可用工具:
        {json.dumps(available, indent=2)}
        
        请选择合适的工具组合来完成任务。
        你必须考虑:
        1. 工具是否能完成所需功能
        2. 工具之间是否能协同
        3. 是否有更简单的替代方案
        4. 成本和可靠性
        
        输出工具链和理由。
        """)
        
        return tool_chain

4.4 遇到障碍自主解决

class ObstacleHandler:
    """
    Agent 遇到障碍时的自主决策。
    """
    
    async def handle(self, agent: Agent, task: Task, error: Error) -> Resolution:
        """
        不预设错误处理流程,让 AI 自己诊断和解决。
        """
        
        diagnosis = await llm.generate(f"""
        任务: {task.description}
        当前状态: {agent.current_state}
        遇到的错误: {error.message}
        错误上下文: {error.context}
        
        请诊断:
        1. 这个错误的根本原因是什么?
        2. 有哪些可能的解决方案?
        3. 每个方案的风险和成本?
        4. 你推荐哪个方案?
        """)
        
        # 根据诊断自主执行修复
        if diagnosis.recommended_action.type == "search_alternative":
            # 搜索替代方案
            alternative = await agent.search(diagnosis.recommended_action.query)
            return await agent.retry_with(alternative)
            
        elif diagnosis.recommended_action.type == "decompose_further":
            # 任务太复杂,需要进一步拆分
            subtasks = await MissionDecomposer().decompose(task)
            return await agent.execute_parallel(subtasks)
            
        elif diagnosis.recommended_action.type == "escalate":
            # 无法自主解决,上报
            return Escalation(reason=diagnosis.root_cause, suggested_help=diagnosis.needs)
            
        elif diagnosis.recommended_action.type == "retry_with_adjustment":
            # 调整参数重试
            return await agent.retry_with_adjustment(diagnosis.adjustment)

6. 人机协作层:Human-in-the-Loop

6.1 核心思想:AI 不是孤岛

蜂群再智能,也有必须人类介入的边界:

  • 💰 资金操作:充值 API 额度、购买云服务
  • 🔑 密钥配置:填写 API Key、配置 OAuth
  • 🏗️ 资源申请:开通服务器权限、申请域名备案
  • 关键决策:技术选型分歧需要人类拍板、架构方向确认
  • 🔒 安全审批:生产环境部署、数据库变更、密钥轮换

AI 的职责不是绕过人类,而是:

  1. 精准识别何时必须人类介入
  2. 清晰表达需要什么、为什么需要、什么时候要
  3. 优雅暂停工作流,不阻塞其他可并行任务
  4. 自动恢复人类响应后立即继续
  5. 主动跟进长时间未响应时提醒

6.2 人机交互类型

类型场景AI 行为人类响应方式
信息收集需要业务背景知识提问并给出选项选择或文字回复
权限申请需要 API Key / Token生成申请表单填写并提交
资金操作API 额度不足生成充值链接 + 成本说明点击支付
决策确认技术选型分歧给出对比报告 + 推荐确认或否决
安全审批生产部署生成变更清单 + 风险说明批准或驳回
验收确认功能完成待上线生成演示 + 测试报告确认或打回

6.3 人机协作协议

class HumanInTheLoop:
    """
    人机协作中枢:AI 主动、清晰、礼貌地向人类求助
    """
    
    async def request(self, agent: Agent, need: HumanNeed) -> HumanResponse:
        """
        AI 向人类发起请求的标准流程
        """
        
        # 1. 生成请求(结构化、可执行)
        request = await self._craft_request(agent, need)
        
        # 2. 记录到待处理队列(支持异步)
        ticket = await self._create_ticket(request)
        
        # 3. 通知人类(多渠道)
        await self._notify_human(request, urgency=need.urgency)
        
        # 4. 暂停当前 Agent(但不阻塞整个蜂群)
        agent.state = "WAITING_FOR_HUMAN"
        
        # 5. 等待响应(轮询 + WebSocket 推送)
        response = await self._wait_for_response(ticket, timeout=need.timeout)
        
        # 6. 恢复执行
        agent.state = "RESUMED"
        return response
    
    async def _craft_request(self, agent: Agent, need: HumanNeed) -> HumanRequest:
        """
        生成清晰、可执行的人类请求
        """
        
        if need.type == "API_KEY":
            return HumanRequest(
                title=f"需要配置 {need.service} API Key",
                body=f"""
                ## 为什么需要
                Agent [{agent.id}] 正在执行任务 [{agent.current_task.id}],
                需要调用 {need.service} 来完成 [{need.purpose}]。
                
                ## 影响
                如果不配置,该任务将无法继续,但其他不依赖此服务的任务仍可并行执行。
                
                ## 操作步骤
                1. 访问 [{need.service_url}]
                2. 创建 API Key(选择权限:{need.required_scopes})
                3. 点击下方输入框粘贴
                
                ## 预计成本
                {need.estimated_cost}/月
                """,
                action_type="INPUT",  # 需要人类输入
                input_schema={"api_key": "string"},
                deadline=need.deadline,
                fallback="如果24小时未响应,将尝试使用免费替代方案"
            )
        
        elif need.type == "RECHARGE":
            return HumanRequest(
                title="API 额度不足,需要充值",
                body=f"""
                ## 当前状况
                剩余额度:${need.remaining_balance}
                本次任务预计消耗:${need.estimated_cost}
                缺口:${need.shortfall}
                
                ## 推荐充值
                金额:${need.recommended_amount}
                理由:可覆盖未来 {need.coverage_sprints} 个 Sprint
                
                ## 支付链接
                [{need.payment_url}]
                
                ## 紧急程度
                {need.urgency}
                """,
                action_type="CLICK",  # 点击链接即可
                fallback="如果2小时未充值,将自动降级到 cheaper model 继续"
            )
        
        elif need.type == "DECISION":
            return HumanRequest(
                title=f"技术选型需要您拍板:{need.decision_topic}",
                body=f"""
                ## 背景
                蜂群在 [{need.task_context}] 遇到选型分歧:
                
                {self._format_options(need.options)}
                
                ## 蜂群涌现倾向
                基于实际行为分析,{need.emergent_winner} 被更多 Agent 采用。
                
                ## 推荐
                {need.recommendation}
                
                ## 操作
                请选择:{[o.name for o in need.options]}
                或回复您的理由,蜂群将按您的决策执行。
                """,
                action_type="SELECT",
                options=[o.name for o in need.options],
                fallback="如果4小时未响应,将采用蜂群涌现共识继续"
            )

6.4 人机通信渠道

class HumanNotification:
    """
    多渠道触达人类,确保请求不被遗漏
    """
    
    async def send(self, request: HumanRequest, profile: UserProfile):
        """根据紧急程度选择渠道组合"""
        
        channels = []
        
        # 所有请求都进 Dashboard
        channels.append(DashboardNotification(request))
        
        # 紧急请求额外推送
        if request.urgency == "HIGH":
            if profile.has_email:
                channels.append(EmailNotification(request))
            if profile.has_slack:
                channels.append(SlackDM(request))
            if profile.has_phone:
                channels.append(SMSNotification(request))
        
        # 关键决策(资金/安全)强制多渠道
        if request.type in ["RECHARGE", "SECURITY_APPROVAL"]:
            channels.append(PushNotification(request))  # 浏览器推送
        
        await asyncio.gather(*[c.send() for c in channels])
    
    async def _dashboard_ui(self, request: HumanRequest) -> dict:
        """Dashboard 中的交互卡片"""
        return {
            "type": "human_request",
            "title": request.title,
            "body": request.body,
            "actions": self._render_actions(request),
            "deadline": request.deadline,
            "blocking_tasks": request.blocking_tasks,
            "other_tasks_still_running": request.non_blocking_tasks,
        }

6.5 优雅暂停与恢复

class GracefulPause:
    """
    需要人类时,只暂停阻塞路径,其他蜂群继续飞
    """
    
    async def handle_human_request(self, swarm: Swarm, ticket: Ticket):
        """
        处理需要人类介入的场景
        """
        
        # 找到被阻塞的任务
        blocked_task = ticket.blocking_task
        
        # 找到依赖此任务的其他任务(也被阻塞)
        downstream = swarm.task_tree.get_downstream(blocked_task)
        
        # 找到不依赖此任务的任务(继续执行)
        independent = [t for t in swarm.task_tree.tasks if t not in downstream and t != blocked_task]
        
        # 暂停阻塞链
        for task in downstream:
            task.state = "PAUSED_WAITING_HUMAN"
            agent = swarm.find_agent_by_task(task)
            if agent:
                agent.state = "IDLE"  # 释放 Agent 去做其他事
        
        # 独立任务继续跑
        await swarm.continue_parallel(independent)
        
        # 等待人类响应
        response = await self.wait_for_ticket(ticket)
        
        # 恢复阻塞链
        if response.approved:
            for task in [blocked_task] + downstream:
                task.state = "READY"
                # 重新分配 Agent 执行
                await swarm.task_board.post_task(task)
        
        return response

6.6 人机协作 Dashboard

┌─────────────────────────────────────────────────────────────────┐
│  [Logo] AI AutoDev Team          [🔔 3 条待处理] [余额: $47.3]   │
├─────────────────────────────────────────────────────────────────┤
│                                                                 │
│  待您处理 (3)                                                   │
│  ┌──────────────────────────────────────────────────────────┐  │
│  │ 🔴 紧急: API 额度不足 (阻塞 2 个任务)                       │  │
│  │    剩余 $2.1,任务预计 $5.4,需要充值 $10                  │  │
│  │    [ 立即充值 ]  [ 先暂停,我稍后处理 ]                      │  │
│  └──────────────────────────────────────────────────────────┘  │
│  ┌──────────────────────────────────────────────────────────┐  │
│  │ 🟡 决策: 数据库选型 (阻塞 1 个任务)                          │  │
│  │    Agent 们用了 PostgreSQL 和 MySQL,需要您确认              │  │
│  │    推荐: PostgreSQL (原因: JSONB 支持更好)                  │  │
│  │    [ 确认 PostgreSQL ]  [ 选 MySQL ]  [ 其他方案 ]          │  │
│  └──────────────────────────────────────────────────────────┘  │
│  ┌──────────────────────────────────────────────────────────┐  │
│  │ 🔵 信息: 需要业务确认                                        │  │
│  │    "注册时是否需要手机号验证?"                              │  │
│  │    [ 需要 ]  [ 不需要 ]  [ 仅邮箱即可 ]                      │  │
│  └──────────────────────────────────────────────────────────┘  │
│                                                                 │
│  正在运行 (不受阻塞影响)                                         │
│  ├─ 前端页面开发 ............................... 78%              │
│  ├─ 单元测试编写 ............................... 45%              │
│  └─ 文档生成 ................................. 90%              │
│                                                                 │
└─────────────────────────────────────────────────────────────────┘

6.7 常见人机协作场景

场景 1:API Key 缺失
Agent-3 正在集成邮件服务,需要 Resend API Key。

AI 行为:
1. 检测环境变量:RESEND_API_KEY 未设置
2. 检测 Resend 文档:需要 API Key
3. 生成请求:"需要配置 Resend API Key"
4. 暂停 Agent-3 的邮件相关任务
5. Agent-1 (前端) 和 Agent-2 (测试) 继续不受影响

人类响应:
→ 点击 Dashboard 输入框 → 粘贴 API Key → 点击确认

AI 行为:
6. 验证 Key 可用(发送测试邮件)
7. 恢复 Agent-3 执行
8. 记录到环境配置(下次复用)
场景 2:预算不足
蜂群执行中,剩余额度 $2.1,当前 Sprint 预估还需 $5.4。

AI 行为:
1. 预测:按当前消耗速度,30 分钟后额度耗尽
2. 评估:降级到 GPT-4o-mini 可以撑 2 小时,但质量下降
3. 生成请求:"API 额度不足,建议充值 $10"
4. 附带:历史消耗趋势图、推荐充值金额理由

人类响应:
→ 点击充值链接 → 支付 $10 → 系统检测到额度更新

AI 行为:
5. 恢复所有 Agent 全力运行
6. 记录:此 Sprint 因充值中断 15 分钟
场景 3:技术选型分歧
3 个 Agent 分别选了 PostgreSQL、MySQL、SQLite。

AI 行为:
1. 收集各 Agent 的选型理由(Stigmergy 痕迹)
2. 分析:PostgreSQL 被 2 个 Agent 实际采用,SQLite 被 1 个
3. 生成 ADR(架构决策记录)草案
4. 生成请求:"数据库选型需要确认"
5. 附带:对比表、蜂群倾向、推荐

人类响应:
→ 选择 PostgreSQL → 添加备注 "同意,长期项目需要扩展性"

AI 行为:
6. 采用 PostgreSQL 的 Agent 继续
7. 采用 SQLite 的 Agent 自动迁移到 PostgreSQL
8. 最终 ADR 记录人类决策理由
场景 4:安全审批
蜂群完成任务,准备部署到生产环境。

AI 行为:
1. 检测:涉及数据库 Schema 变更(新增 User 表)
2. 生成变更清单:DDL 语句、回滚脚本、影响范围
3. 生成请求:"生产部署需审批"
4. 附带:风险评估、回滚方案、测试报告

人类响应:
→ 查看变更清单 → 确认测试通过 → 点击批准

AI 行为:
5. 执行部署(在维护窗口)
6. 监控 5 分钟,确认无异常
7. 生成部署报告

6.8 人机协作原则

原则说明
不阻塞全局需要人类的任务暂停,其他独立任务继续
一次说清请求包含:背景、影响、操作步骤、截止时间、备选方案
减少摩擦提供一键操作(点击确认、一键充值),不让用户输入复杂内容
上下文保留人类响应后,AI 知道之前发生了什么,无需重复解释
礼貌提醒快到期时礼貌提醒,不骚扰,提供"稍后处理"选项
学习偏好记录人类的常见决策模式,下次主动推荐

7. 边界约束系统(唯一硬编码的规则)

5.1 约束类型

@dataclass
class ConstraintSystem:
    """
    人类只定义边界,不定义过程。
    """
    
    # === 技术约束 ===
    tech_stack: Optional[List[str]] = None  # ["nextjs", "prisma", "typescript"]
    forbidden_tech: Optional[List[str]] = None  # ["jquery", "php"]
    
    # === 安全边界 ===
    forbidden_paths: List[str] = field(default_factory=list)  # ["/etc", "~/.ssh"]
    forbidden_operations: List[str] = field(default_factory=list)  # ["rm -rf /", "drop table"]
    network_allowlist: Optional[List[str]] = None  # ["api.github.com", "registry.npmjs.org"]
    
    # === 资源约束 ===
    budget_usd: float = 10.0  # 本次任务预算上限
    time_limit_minutes: int = 120
    token_limit: int = 100000
    
    # === 质量约束 ===
    min_test_coverage: float = 80.0
    required_deliverables: List[str] = field(default_factory=list)  # ["code", "tests", "docs"]
    
    # === 范围约束 ===
    scope_in: List[str] = field(default_factory=list)  # 必须包含
    scope_out: List[str] = field(default_factory=list)  # 明确排除

# 约束检查器
class ConstraintEnforcer:
    """所有 Agent 行为必须通过约束检查"""
    
    async def check(self, action: AgentAction, constraints: ConstraintSystem) -> bool:
        # 检查安全边界
        if action.fetches.any(path in constraints.forbidden_paths):
            return False, f"禁止访问 {path}"
        
        # 检查预算
        if action.estimated_cost + self.spent > constraints.budget_usd:
            return False, f"超出预算: {action.estimated_cost} > 剩余 {constraints.budget_usd - self.spent}"
        
        # 检查技术栈
        if action.uses_tech not in constraints.tech_stack:
            return False, f"不允许使用 {action.uses_tech}"
        
        return True, "通过"

5.2 约束示例

# 人类输入的约束(YAML 格式)
mission: "实现用户注册模块,含邮箱验证码"

constraints:
  tech_stack:
    - nextjs
    - prisma
    - typescript
    - tailwindcss
  
  forbidden_tech:
    - jquery
    - php
    - python  # 前端项目不许混 Python
  
  budget_usd: 5.0
  time_limit_minutes: 90
  
  quality:
    min_test_coverage: 80
    required_deliverables:
      - code
      - tests
      - architecture_decision_record  # 为什么选 Resend 而不是 SendGrid
      - demo_screenshot
  
  security:
    forbidden_operations:
      - "DELETE FROM"
      - "DROP TABLE"
      - "rm -rf"
    forbidden_paths:
      - "/etc"
      - "~/.ssh"
    network_allowlist:
      - "registry.npmjs.org"
      - "api.resend.com"
  
  scope:
    in:
      - "用户注册表单"
      - "邮箱验证码发送"
      - "验证码校验"
      - "密码存储(bcrypt)"
    out:
      - "OAuth 第三方登录"
      - "手机号验证码"
      - "管理后台"

8. 验证层:不通过就不算完成

6.1 验证即契约

class VerificationEngine:
    """
    每个子任务必须有客观、自动、无歧义的验证。
    AI 自己生成验证方式,人类只审查验证是否合理。
    """
    
    async def verify(self, task: Task, result: TaskResult) -> VerificationResult:
        """
        根据任务定义的 verification spec 自动验证。
        """
        
        spec = task.verification
        
        if spec.type == "file_exists":
            exists = await self._check_file_exists(spec.path)
            return VerificationResult(passed=exists, detail=f"{spec.path} 存在: {exists}")
            
        elif spec.type == "command_exit_0":
            proc = await asyncio.create_subprocess_shell(
                spec.command,
                stdout=asyncio.subprocess.PIPE,
                stderr=asyncio.subprocess.PIPE
            )
            stdout, stderr = await asyncio.wait_for(proc.communicate(), timeout=spec.timeout_seconds)
            passed = proc.returncode == 0
            return VerificationResult(
                passed=passed,
                detail=f"命令: {spec.command}\n退出码: {proc.returncode}\n输出: {stdout.decode()[:500]}"
            )
            
        elif spec.type == "coverage_threshold":
            coverage = await self._parse_coverage_report(result.test_output)
            passed = coverage >= spec.min_coverage
            return VerificationResult(
                passed=passed,
                detail=f"覆盖率: {coverage}% (要求 ≥ {spec.min_coverage}%)"
            )
            
        elif spec.type == "custom_script":
            # 运行自定义验证脚本
            result = await self._run_custom_verifier(spec.script_path, result)
            return result

### 6.2 验证类型补充 (v2.1 新增)

> 原文档验证类型覆盖不足,新增以下类型以提高验证覆盖率。

```python
@dataclass
class VerificationType(Enum):
    """扩展的验证类型列表"""

    # === 基础验证 (原有) ===
    FILE_EXISTS = "file_exists"           # 文件存在性
    COMMAND_EXIT_0 = "command_exit_0"     # 命令退出码为 0
    COVERAGE_THRESHOLD = "coverage_threshold"  # 测试覆盖率
    CURL_200 = "curl_200"                 # HTTP 请求返回 200
    E2E_PASS = "e2e_pass"                 # E2E 测试通过

    # === 新增:代码质量验证 (v2.1) ===
    LINT_PASS = "lint_pass"               # 代码风格检查通过 (ESLint/Pylint)
    TYPE_CHECK = "type_check"              # 类型检查通过 (TypeScript/mypy)
    NO_SECURITY_VULNS = "no_security_vulns"  # 无安全漏洞 (Semgrep/Bandit)

    # === 新增:功能正确性验证 (v2.1) ===
    SCHEMA_VALID = "schema_valid"          # 数据库 Schema 验证通过
    API_CONTRACT = "api_contract"           # API 响应符合 OpenAPI Schema
    LOGIC_ASSERT = "logic_assert"           # 业务逻辑断言 (自定义检查)

    # === 新增:运行时行为验证 (v2.1) ===
    MEMORY_USAGE = "memory_usage"           # 内存使用在限制内
    RESPONSE_TIME = "response_time"         # 响应时间符合要求
    CONCURRENT_PASS = "concurrent_pass"     # 并发测试通过

    # === 新增:数据验证 (v2.1) ===
    DB_MIGRATION = "db_migration"           # 数据库迁移成功
    DB_ROLLBACK = "db_rollback"             # 数据库回滚测试通过
    DATA_INTEGRITY = "data_integrity"       # 数据完整性检查通过

验证类型使用场景:

验证类型适用场景示例
LINT_PASS所有代码任务npx eslint src/
TYPE_CHECKTypeScript/Python 项目npx tsc --noEmit / mypy src/
NO_SECURITY_VULNS安全敏感任务semgrep --config=auto .
SCHEMA_VALID数据库 Schema 变更prisma validate
API_CONTRACTAPI 开发验证响应 JSON 符合 Schema
LOGIC_ASSERT业务逻辑验证自定义断言脚本
RESPONSE_TIMEAPI 性能验证curl -w "%{time_total}"
DB_MIGRATION数据库迁移任务prisma migrate dev
DATA_INTEGRITY数据处理任务检查记录数、字段完整性

验证结果结构:

@dataclass
class VerificationResult:
    """验证结果"""
    passed: bool
    type: str                    # 验证类型
    detail: str                 # 详细输出
    duration_ms: int            # 验证耗时
    cost_usd: float = 0.0       # 验证消耗成本
    error_code: str = None      # 如果失败,错误码

    @property
    def summary(self) -> str:
        status = "✅ PASS" if self.passed else "❌ FAIL"
        return f"{status} [{self.type}] {self.detail[:100]}"
async def auto_fix(self, task: Task, result: TaskResult, verification: VerificationResult):
    """
    验证不通过 → AI 自主分析原因并修复。
    """
    if not verification.passed:
        # 诊断失败原因
        diagnosis = await llm.generate(f"""
        任务: {task.description}
        验证失败: {verification.detail}
        
        请分析:
        1. 为什么验证失败?
        2. 代码或配置需要怎么改?
        3. 修改后如何重新验证?
        """)
        
        # 执行修复
        fix_result = await agent.execute(diagnosis.fix_plan)
        
        # 重新验证
        return await self.verify(task, fix_result)

### 6.2 验收报告

```yaml
# 自动生成的验收报告
mission: "实现用户注册模块"
status: PASSED  # 所有子任务验证通过

tasks:
  - id: T1
    description: "设计数据库 Schema"
    verification: "prisma validate 通过"
    result: PASSED
    attempts: 1
    cost: "$0.2"
    
  - id: T2
    description: "实现注册 API"
    verification: "curl 返回 200 && 数据库有记录"
    result: PASSED
    attempts: 2  # 第一次 bcrypt 配置错了,自动修复
    cost: "$0.6"
    
  - id: T3
    description: "集成邮箱服务"
    verification: "测试邮箱收到邮件 && 验证码可校验"
    result: PASSED
    attempts: 3
    cost: "$1.2"
    # ADR: 为什么选 Resend
    decision_record: |
      搜索对比了 SendGrid ($0.10/封)、Resend ($0.0001/封)、AWS SES ($0.10/封)。
      对于验证码场景(低频率),Resend 免费额度足够,API 最简单,故选择。
      备选: 如果量上去,可迁移到 AWS SES。
    
  - id: T4
    description: "前端注册页面"
    verification: "Playwright E2E 通过"
    result: PASSED
    cost: "$0.8"
    
  - id: T5
    description: "测试覆盖"
    verification: "coverage ≥ 80%"
    result: PASSED
    actual_coverage: 83.2%
    cost: "$0.4"

total_cost: "$3.2 / $5.0"
total_time: "47分钟 / 90分钟"
auto_fixes: 2  # AI 自主修复了 2 次错误
human_interventions: 1  # 1 次请求 API Key 配置
escalations: 0  # 没有无法解决需要人工接管的情况

7. 工具自治层(Tool Mesh)

7.1 核心思想

Agent 不依赖预设工具列表。遇到任务时:

  1. 搜索——系统里有什么工具?网络上有什么?
  2. 评估——哪个最适合当前任务?
  3. 获取——没有的话自动安装/配置
  4. 调用——标准化接口执行

7.2 工具发现

class ToolDiscovery:
    """
    自动发现所有可用工具和能力。
    """
    
    async def discover_all(self) -> ToolCatalog:
        catalog = ToolCatalog()
        
        # 1. 扫描本地 OpenClaw Skills
        catalog.add(await self._scan_skills("~/.agents/skills/"))
        
        # 2. 扫描 MCP Servers
        catalog.add(await self._scan_mcp_servers())
        
        # 3. 扫描系统命令
        catalog.add(await self._scan_executables())
        
        # 4. 扫描已安装包的能力
        catalog.add(await self._scan_packages())
        
        # 5. 扫描环境 API Keys (判断可用外部服务)
        catalog.add(await self._scan_api_availability())
        
        # 6. 扫描代码仓库历史 (复用已有工具函数)
        catalog.add(await self._scan_codebase_tools())
        
        return catalog

7.3 工具自动获取

class ToolAcquisition:
    """
    当现有工具不够时,自动搜索并获取新工具。
    """
    
    async def acquire(self, need: str, constraints: ConstraintSystem) -> Tool:
        """
        需要: "发送邮件"
        约束: 只能用 Python/TypeScript,预算<$1
        
        自动:
        1. 搜索 PyPI/npm 上邮件相关包
        2. 对比文档完整性、GitHub stars、最近更新
        3. 在沙盒安装测试
        4. 验证可用后纳入 Catalog
        """
        
        # 搜索候选
        candidates = await self._search_packages(need, constraints.tech_stack)
        
        # 评估 (多维度)
        scored = []
        for cand in candidates:
            score = await self._evaluate(cand, criteria=[
                "stars",
                "last_update_within_6_months",
                "has_typescript_definitions",
                "license_compatible",
                "install_size_under_10mb"
            ])
            scored.append((cand, score))
        
        # 选择最佳
        best = max(scored, key=lambda x: x[1])
        
        # 沙盒安装验证
        installed = await self._sandbox_install(best[0])
        test_pass = await self._verify_tool_works(installed, need)
        
        if test_pass:
            return installed
        else:
            # 试下一个
            return await self._try_next(scored)

8. LLM 调用策略 (新增)

本章定义 Agent 执行时使用哪个 LLM、如何动态降级、成本如何控制。 没有策略的 LLM 调用是成本失控的根源。

8.1 模型分级

class LLMModelTier:
    """
    LLM 模型分级,按能力和成本递增。
    """
    # 级别 1:低成本,小任务
    HAIKU = {
        "name": "claude-haiku-4-5-20251101",
        "cost_per_1k_input": 0.0008,
        "cost_per_1k_output": 0.004,
        "context_window": 200000,
        "typical_use": "简单文件操作、文本替换、模式匹配"
    }

    # 级别 2:中成本,常规任务
    SONNET = {
        "name": "claude-sonnet-4-6-20251101",
        "cost_per_1k_input": 0.003,
        "cost_per_1k_output": 0.015,
        "context_window": 200000,
        "typical_use": "代码编写、API 实现、单元测试"
    }

    # 级别 3:高成本,复杂任务
    OPUS = {
        "name": "claude-opus-4-7",
        "cost_per_1k_input": 0.015,
        "cost_per_1k_output": 0.075,
        "context_window": 200000,
        "typical_use": "架构设计、复杂 bug 诊断、多文件重构"
    }

    # 降级选项(OpenAI)
    GPT4O_MINI = {
        "name": "gpt-4o-mini",
        "cost_per_1k_input": 0.00015,
        "cost_per_1k_output": 0.0006,
        "context_window": 128000,
        "typical_use": "预算不足时的降级选项"
    }

8.2 任务复杂度分类器

系统自动判断任务复杂度,决定使用哪个模型层级。

class TaskComplexityClassifier:
    """
    任务复杂度分类器:自动评估任务需要什么级别的模型。
    """

    async def classify(self, task: Task) -> LLMModelTier:
        """
        根据任务特征评估复杂度。
        """

        complexity_score = 0

        # 因素 1:任务涉及的文件数量
        if task.depends_on_files:
            file_count = len(task.depends_on_files)
            complexity_score += min(file_count * 0.2, 2.0)  # 最多 +2

        # 因素 2:是否涉及多技术栈交互
        tech_stack_mix = len(task.required_tech_stacks)
        complexity_score += tech_stack_mix * 0.5  # 每个技术栈 +0.5

        # 因素 3:任务描述的语义复杂度
        semantic_complexity = self._estimate_semantic_complexity(task.description)
        complexity_score += semantic_complexity

        # 因素 4:是否涉及决策/架构设计
        if any(keyword in task.description.lower()
               for keyword in ["设计", "架构", "方案", "选择", "决策"]):
            complexity_score += 1.5

        # 因素 5:是否涉及未知领域
        if task.unknown_domain:
            complexity_score += 1.0

        # 映射到模型层级
        if complexity_score < 2.0:
            return LLMModelTier.HAIKU
        elif complexity_score < 4.0:
            return LLMModelTier.SONNET
        else:
            return LLMModelTier.OPUS

    def _estimate_semantic_complexity(self, description: str) -> float:
        """
        简单启发式评估语义复杂度。
        实际实现可由 LLM 辅助判断。
        """
        score = 0.0

        # 句子越多越复杂
        sentences = description.count("。") + description.count(".")
        score += min(sentences * 0.1, 1.0)

        # 连接词越多越复杂
        connectors = ["并且", "而且", "同时", "此外", "但是", "然而", "然而", "所以", "因此", "然而"]
        score += sum(0.15 for c in connectors if c in description)

        return min(score, 2.0)

复杂度评分因素:

因素权重说明
文件数量0.2/个最多 +2
技术栈种类0.5/种跨栈越多越复杂
语义复杂度0-2句子数、连接词密度
决策/架构关键词+1.5含"设计/架构/方案"
未知领域+1.0任务描述涉及陌生技术

8.3 动态降级策略

当预算不足或响应超时,自动降级到更便宜的模型。

class LLMDynamicDowngrade:
    """
    LLM 动态降级策略。
    """

    async def execute_with_fallback(
        self,
        task: Task,
        preferred_tier: LLMModelTier,
        budget_remaining: float
    ) -> LLMResult:
        """
        执行 LLM 调用,必要时降级。
        """

        # 预估当前层级的成本
        estimated_cost = self._estimate_cost(task, preferred_tier)

        # 如果预估成本超过预算的 30%,考虑降级
        if estimated_cost > budget_remaining * 0.3:
            preferred_tier = self._try_downgrade(preferred_tier)

        # 执行调用
        result = await self._call_llm(task, preferred_tier)

        # 如果超时,尝试降级
        if result.timeout and preferred_tier != LLMModelTier.HAIKU:
            result = await self._call_llm(task, LLMModelTier.HAIKU)

        return result

    def _try_downgrade(self, tier: LLMModelTier) -> LLMModelTier:
        """尝试降级到下一级"""
        downgrade_map = {
            LLMModelTier.OPUS: LLMModelTier.SONNET,
            LLMModelTier.SONNET: LLMModelTier.HAIKU,
            LLMModelTier.HAIKU: LLMModelTier.GPT4O_MINI
        }
        return downgrade_map.get(tier, tier)

降级触发条件:

触发条件降级策略
预算剩余 < 20%强制降一级
单次调用超时 > 30s降一级重试
连续 3 次 OPUS 失败降级到 SONNET
任务预估成本 > 预算 30%降级到更低层级

8.4 成本控制机制

class CostController:
    """
    成本控制器:实时监控和限制 LLM 调用成本。
    """

    def __init__(self, budget_usd: float, mission_id: str):
        self.budget_usd = budget_usd
        self.mission_id = mission_id
        self.spent_usd = 0.0
        self.alert_threshold = 0.8  # 80% 时告警

    async def check_and_charge(self, estimated_cost: float) -> bool:
        """
        检查预算是否足够,预扣费用。
        返回 True 表示可以继续,False 表示预算不足。
        """

        if self.spent_usd + estimated_cost > self.budget_usd:
            # 预算不足,触发人类介入
            await self._request_budget_increase()
            return False

        self.spent_usd += estimated_cost  # 预扣

        # 告警
        if self.spent_usd > self.budget_usd * self.alert_threshold:
            await self._send_budget_alert()

        return True

    async def _request_budget_increase(self):
        """预算不足时创建人机协作票"""
        await human_ticket_manager.create(
            type="RECHARGE",
            title="预算不足,需要充值",
            body=f"已消耗 ${self.spent_usd:.2f} / ${self.budget_usd:.2f}",
            urgency="HIGH"
        )

8.5 Token 使用优化

class TokenOptimizer:
    """
    Token 使用优化:减少不必要的上下文开销。
    """

    def optimize_prompt(self, prompt: str, context: dict) -> str:
        """
        优化 prompt,减少 token 消耗。
        """

        # 移除冗余的示例代码
        prompt = self._trim_excessive_examples(prompt)

        # 压缩技术文档中的空白
        prompt = self._compress_whitespace(prompt)

        # 只传递必要的上下文(而非全部)
        if context.get("file_count", 0) > 5:
            # 只传递关键文件路径,Agent 需要时再读取
            key_files = self._select_key_files(context["files"], k=5)
            prompt = prompt.replace(
                f"相关文件: {context['files']}",
                f"关键文件: {key_files}"
            )

        return prompt

    def estimate_tokens(self, text: str) -> int:
        """
        粗略估算 token 数量(实际按 Provider 计数)。
        英文约 4 字符/token,中文约 2 字符/token。
        """
        return int(len(text) / 3)

9. 任务复杂度分类器 (新增)

本章定义如何判断任务是"简单"还是"复杂",决定用单 Agent 还是蜂群。

9.1 复杂度分级

@dataclass
class TaskComplexity:
    level: str  # "simple" / "medium" / "complex" / "very_complex"
    score: float  # 0.0 - 10.0
    reasons: List[str]  # 为什么这么判断
    recommended_mode: str  # "single" / "swarm_small" / "swarm_medium" / "swarm_large"
    estimated_cost_usd: float  # 预估成本

class TaskComplexityScorer:
    """
    任务复杂度评分器。
    """

    async def score(self, task: Task) -> TaskComplexity:
        """
        综合评估任务复杂度。
        """

        factors = []

        # 因素 1:代码库规模
        codebase_size = task.codebase_size_mb or 0
        if codebase_size > 100:
            factors.append(("LARGE_CODEBASE", 2.0, "代码库 > 100MB"))
        elif codebase_size > 50:
            factors.append(("MEDIUM_CODEBASE", 1.0, "代码库 50-100MB"))

        # 因素 2:跨文件程度
        files_affected = task.estimated_files_affected or 0
        if files_affected > 10:
            factors.append(("MANY_FILES", 2.0, f"涉及 {files_affected} 个文件"))
        elif files_affected > 5:
            factors.append(("SOME_FILES", 1.0, f"涉及 {files_affected} 个文件"))

        # 因素 3:技术栈数量
        tech_count = len(task.required_tech_stacks or [])
        if tech_count > 3:
            factors.append(("MULTI_STACK", 1.5, f"涉及 {tech_count} 个技术栈"))

        # 因素 4:决策点数量
        decisions = task.decision_points or 0
        if decisions > 5:
            factors.append(("MANY_DECISIONS", 2.0, f"需要 {decisions} 个决策"))
        elif decisions > 2:
            factors.append(("SOME_DECISIONS", 1.0, f"需要 {decisions} 个决策"))

        # 因素 5:不确定性
        if task.has_unknown_dependencies:
            factors.append(("UNCERTAINTY", 1.5, "存在未知依赖"))
        if task.has_external_api:
            factors.append(("EXTERNAL_API", 1.0, "需要调用外部 API"))

        # 计算总分
        total_score = sum(f[1] for f in factors)

        # 映射到等级
        if total_score < 2.0:
            level = "simple"
            mode = "single"
        elif total_score < 4.0:
            level = "medium"
            mode = "swarm_small"  # 2 Agent
        elif total_score < 6.0:
            level = "complex"
            mode = "swarm_medium"  # 3 Agent
        else:
            level = "very_complex"
            mode = "swarm_large"  # 5 Agent

        return TaskComplexity(
            level=level,
            score=total_score,
            reasons=[f[2] for f in factors],
            recommended_mode=mode,
            estimated_cost_usd=self._estimate_cost(total_score)
        )

9.2 复杂度分级定义

等级分值特征推荐模式预估成本
简单 (simple)< 2单文件、单一技术栈、无决策单 Agent< $0.5
中等 (medium)2-42-5 个文件、多技术栈、有 API 调用2 Agent 蜂群$0.5-1.5
复杂 (complex)4-6多文件、复杂逻辑、多个决策点3 Agent 蜂群$1.5-3.0
非常复杂 (very_complex)> 6大代码库、多技术栈、高不确定性5 Agent 蜂群$3.0-8.0

9.3 复杂度与蜂群规模决策表

任务类型复杂度推荐方案并行度
简单脚本修改simple单 Agent1
API 实现(单端点)medium单 Agent 或 2 Agent 冗余1-2
多端点 API 开发complex3 Agent(1 架构 + 2 编码)3
技术选型调研medium3 Agent(各调研 1 个方案)3
Bug 修复(已知原因)simple单 Agent1
Bug 修复(未知原因)complex2 Agent 双路排查2
复杂重构very_complex2 Agent(1 重构 + 1 验证)2
新功能模块开发complex3 Agent(前端 + 后端 + 测试)3
端到端功能(页面+API+DB)very_complex3-5 Agent 流水线3-5

9.4 自动决策流程

async def decide_execution_mode(task: Task, budget: float) -> ExecutionPlan:
    """
    自动决定执行模式。
    """

    complexity = await complexity_scorer.score(task)

    # 预算检查
    if complexity.estimated_cost_usd > budget * 0.5:
        # 如果预估成本超过预算的 50%,尝试降低复杂度
        complexity = await _reduce_complexity(task)

    # 生成执行计划
    if complexity.level == "simple":
        return ExecutionPlan(mode="single", agent_count=1)

    elif complexity.level == "medium":
        return ExecutionPlan(mode="swarm_small", agent_count=2)

    elif complexity.level == "complex":
        return ExecutionPlan(mode="swarm_medium", agent_count=3)

    else:  # very_complex
        if budget > 10.0:
            return ExecutionPlan(mode="swarm_large", agent_count=5)
        else:
            # 预算不足,降低并行度
            return ExecutionPlan(mode="swarm_medium", agent_count=3)

10. 错误分类与处理规范 (新增)

本章定义 Agent 执行过程中可能遇到的错误类型及标准处理方式。

10.1 错误分类体系

class ErrorCategory(Enum):
    """
    错误分类:定义所有可处理的错误类型。
    """

    # === 可自愈错误(Agent 自动处理)===

    TRANSIENT = "TRANSIENT"  # 瞬时错误,如网络抖动
    RETRYABLE = "RETRYABLE"  # 可重试错误,如超时
    VALIDATION = "VALIDATION"  # 验证失败,如输入不合法

    # === 需人工处理错误(创建 HumanTicket)===

    RESOURCE = "RESOURCE"  # 资源不足,如 API Key 缺失、额度不足
    PERMISSION = "PERMISSION"  # 权限不足,如禁止路径访问
    DECISION = "DECISION"  # 需要决策,如技术选型分歧
    SECURITY = "SECURITY"  # 安全相关,如生产环境变更

    # === 不可恢复错误(任务失败)===

    UNSUPPORTED = "UNSUPPORTED"  # 不支持的功能
    TIMEOUT = "TIMEOUT"  # 执行超时
    CORRUPT = "CORRUPT"  # 数据损坏


@dataclass
class ErrorClassification:
    category: ErrorCategory
    code: str  # 具体错误码
    message: str  # 人类可读的错误描述
    retryable: bool  # 是否可重试
    requires_human: bool  # 是否需要人类介入
    resolution: str  # 解决建议

10.2 错误处理决策树

async def handle_error(
    error: Exception,
    context: ExecutionContext
) -> ErrorResolution:
    """
    错误处理决策树。
    """

    classification = classify_error(error)

    # 可自愈错误:自动重试
    if classification.category in [ErrorCategory.TRANSIENT, ErrorCategory.RETRYABLE]:
        if classification.retryable and context.attempt < 3:
            return ErrorResolution(
                action="RETRY",
                message=f"自动重试 ({context.attempt + 1}/3)",
                backoff_seconds=classification.backoff_seconds
            )
        else:
            # 重试耗尽,标记为失败
            return ErrorResolution(
                action="FAIL",
                message=f"重试 {context.attempt} 次后仍失败: {classification.message}"
            )

    # 验证失败:诊断并修复
    if classification.category == ErrorCategory.VALIDATION:
        diagnosis = await _diagnose_validation_error(error, context)
        if diagnosis.can_fix:
            return ErrorResolution(
                action="SELF_FIX",
                diagnosis=diagnosis
            )
        else:
            return ErrorResolution(
                action="ESCALATE",
                reason=diagnosis.reason
            )

    # 需要人类介入:创建 Ticket
    if classification.requires_human:
        ticket = await human_ticket_manager.create(
            type=classification.human_ticket_type,
            title=classification.message,
            body=classification.resolution,
            urgency=classification.urgency,
            blocking_tasks=[context.task_id]
        )
        return ErrorResolution(
            action="PAUSE_WAIT_HUMAN",
            ticket_id=ticket.id
        )

    # 不可恢复错误
    return ErrorResolution(
        action="FAIL",
        message=classification.message
    )

10.3 常见错误处理规范

错误场景分类处理方式重试策略
网络超时TRANSIENT等 2s 重试最多 3 次
LLM 调用失败RETRYABLE等 5s 重试最多 3 次
文件不存在VALIDATION诊断并重新获取不重试
API Key 缺失RESOURCE创建 HumanTicket不重试
预算不足RESOURCE创建 HumanTicket不重试
权限不足PERMISSION创建 HumanTicket不重试
技术选型分歧DECISION创建 HumanTicket不重试
执行超时 5minTIMEOUT任务失败不重试
沙盒崩溃TRANSIENT重新创建沙盒最多 2 次

10.4 错误恢复流程

async def error_recovery_loop(
    task: Task,
    executor: AgentExecutor,
    max_attempts: int = 3
) -> TaskResult:
    """
    错误自动恢复循环。
    """

    for attempt in range(max_attempts):
        try:
            result = await executor.execute_task(task)

            if result.success:
                return result

            # 失败,分析原因
            classification = classify_error(result.error)

            if classification.requires_human:
                # 需要人类,暂停等待
                return result

            if classification.retryable and attempt < max_attempts - 1:
                # 重试
                await asyncio.sleep(classification.backoff_seconds)
                continue

            # 不可恢复失败
            return result

        except SandboxCrash:
            # 沙盒崩溃,重新创建
            if attempt < max_attempts - 1:
                executor.sandbox_manager.recreate()
                continue
            return TaskResult.error("SANDBOX_CRASH", "沙盒连续崩溃")

    return TaskResult.error("MAX_ATTEMPTS", f"达到最大重试次数 {max_attempts}")

11. 前端设计:只展示结果,不 micromanage

8.1 设计哲学

不展示展示
Agent 内部对话当前进度百分比
Agent 选了什么工具任务完成/失败状态
Agent 之间怎么争论验证是否通过
每次 LLM 调用成本累计
Worktree 内部文件最终交付物链接

8.2 核心页面

任务提交页
┌─────────────────────────────────────────────────────────────┐
│  [Logo] AI AutoDev Team                    [余额: $47.3]    │
├─────────────────────────────────────────────────────────────┤
│                                                             │
│  新任务                                                      │
│  ┌─────────────────────────────────────────────────────┐  │
│  │ 描述任务...                                            │  │
│  │ "实现一个支持邮箱验证码的用户注册模块,包含前端表单      │  │
│  │  和后端 API"                                            │  │
│  └─────────────────────────────────────────────────────┘  │
│                                                             │
│  约束 (可选)                                                  │
│  ┌─────────────┐ ┌─────────────┐ ┌─────────────────────────┐│
│  │ 技术栈       │ │ 预算        │ │ 质量标准                 ││
│  │ □ Next.js    │ │ $ 5         │ │ □ 测试覆盖 ≥ 80%         ││
│  │ □ Prisma     │ │             │ │ □ 包含 E2E 测试          ││
│  │ □ TypeScript │ │ 时间: 90分钟 │ │ □ 包含 ADR 文档          ││
│  └─────────────┘ └─────────────┘ └─────────────────────────┘│
│                                                             │
│  安全边界                                                     │
│  ☑ 禁止访问 /etc     ☑ 禁止 rm -rf    ☑ 禁止 DROP TABLE      │
│                                                             │
│                    [ 🚀 开始执行 ]                            │
│                                                             │
└─────────────────────────────────────────────────────────────┘
执行监控页(极简)
┌─────────────────────────────────────────────────────────────┐
│  任务 #1284: 用户注册模块          [⏳ 执行中 | 已用 $2.1]      │
├─────────────────────────────────────────────────────────────┤
│                                                             │
│  进度: ████████████████░░░░  67%                              │
│                                                             │
│  子任务状态:                                                  │
│  ✓ 数据库 Schema         ✓ 注册 API        ⏳ 邮箱集成         │
│  ○ 前端页面             ○ 测试覆盖                                 │
│                                                             │
│  [ 实时日志 ]  [ 交付物 ]  [ 验证报告 ]                        │
│                                                             │
│  --- 实时日志 (最近 5 条) ---                                 │
│  14:32:01  [OK]   T1 数据库验证通过                           │
│  14:32:15  [OK]   T2 API 测试通过 (200 OK)                   │
│  14:35:22  [INFO] T3 搜索邮件服务: 选中 Resend (免费额度充足)    │
│  14:36:01  [WARN] T3 第一次验证码发送失败,自动重试中...       │
│  14:36:45  [OK]   T3 验证码发送成功,正在集成...              │
│                                                             │
└─────────────────────────────────────────────────────────────┘
结果报告页
┌─────────────────────────────────────────────────────────────┐
│  任务 #1284 已完成 ✅                                          │
├─────────────────────────────────────────────────────────────┤
│                                                             │
│  交付物                                                      │
│  📁 代码仓库: git@github.com/.../feat/register-module        │
│  📊 测试报告: 覆盖率 83.2% | 12 passed, 0 failed             │
│  📝 ADR 文档: 为什么选 Resend 而不是 SendGrid               │
│  🖼️  演示截图: [点击查看]                                      │
│                                                             │
│  资源消耗                                                    │
│  费用: $3.2 / $5.0      时间: 47分钟 / 90分钟                 │
│  LLM 调用: 23 次         自动修复: 2 次                       │
│                                                             │
│  [下载 ZIP]  [查看 PR]  [部署到预览环境]  [标记成功]            │
│                                                             │
└─────────────────────────────────────────────────────────────┘

9. 后端架构:极简核心

9.1 核心只有 3 个服务

┌─────────────────────────────────────────────────────────────┐
│                    API Gateway (FastAPI)                    │
│         /mission/create  /mission/{id}/status               │
│         /mission/{id}/results  /health                     │
├─────────────────────────────────────────────────────────────┤
│                  Mission Controller                         │
│    接收任务 → 调用 Decomposer → 调度 Agents → 收集结果      │
│    只做调度,不做任何业务逻辑                                │
├─────────────────────────────────────────────────────────────┤
│                   Agent Worker Pool                         │
│    ┌─────────┐ ┌─────────┐ ┌─────────┐                    │
│    │ Agent-1 │ │ Agent-2 │ │ Agent-N │  (动态扩缩容)       │
│    │ 自治执行 │ │ 自治执行 │ │ 自治执行 │                    │
│    └─────────┘ └─────────┘ └─────────┘                    │
├─────────────────────────────────────────────────────────────┤
│                    Verification Engine                      │
│    运行验证命令 → 返回通过/失败 → 触发修复或上报            │
├─────────────────────────────────────────────────────────────┤
│                    Tool Mesh Gateway                        │
│    统一工具接口: MCP + Skills + System Commands + Web Search │
└─────────────────────────────────────────────────────────────┘

9.2 数据模型(极简)

-- 只需要 3 张表

CREATE TABLE missions (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    description TEXT NOT NULL,
    constraints JSONB NOT NULL DEFAULT '{}',
    status VARCHAR(20) DEFAULT 'pending',  -- pending/running/completed/failed
    result JSONB,
    cost_usd DECIMAL(10,4) DEFAULT 0,
    created_at TIMESTAMPTZ DEFAULT now(),
    completed_at TIMESTAMPTZ
);

CREATE TABLE tasks (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    mission_id UUID REFERENCES missions(id),
    description TEXT NOT NULL,
    deliverable TEXT NOT NULL,
    verification_type VARCHAR(50),
    verification_command TEXT,
    status VARCHAR(20) DEFAULT 'pending',
    attempts INTEGER DEFAULT 0,
    cost_usd DECIMAL(10,4) DEFAULT 0,
    result JSONB
);

CREATE TABLE execution_logs (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    mission_id UUID REFERENCES missions(id),
    task_id UUID REFERENCES tasks(id),
    level VARCHAR(20),  -- INFO/WARN/ERROR/OK
    message TEXT,
    metadata JSONB,
    created_at TIMESTAMPTZ DEFAULT now()
);

10. 执行流程(端到端)

Human: "实现用户注册模块"
        │
        ▼
┌─────────────────────────────────────┐
│ MissionController.create_mission()  │
│ 保存任务,生成 mission_id            │
└─────────────────────────────────────┘
        │
        ▼
┌─────────────────────────────────────┐
│ MissionDecomposer.decompose()       │
│ LLM 自主拆解为子任务树               │
│ 每个子任务含验证方式                 │
└─────────────────────────────────────┘
        │
        ▼
┌─────────────────────────────────────┐
│ AgentPool.dispatch()                │
│ 分配 Agent 执行子任务                │
│ Agent 自己决定怎么做                  │
└─────────────────────────────────────┘
        │
        ▼
┌─────────────────────────────────────┐
│ Agent 执行循环:                      │
│ 1. 理解任务                         │
│ 2. 搜索需要的信息                    │
│ 3. 选工具                           │
│ 4. 执行                             │
│ 5. 自我验证                         │
│ 6. 不通过 → 诊断 → 修复 → 重验       │
│ 7. 通过 → 提交结果                   │
└─────────────────────────────────────┘
        │
        ▼
┌─────────────────────────────────────┐
│ VerificationEngine.run_all()        │
│ 按任务定义的验证方式自动验证         │
│ 全部通过 → mission 完成              │
│ 有失败 → 返回 Agent 修复             │
└─────────────────────────────────────┘
        │
        ▼
┌─────────────────────────────────────┐
│ 生成验收报告                         │
│ 通知 Human                          │
└─────────────────────────────────────┘

11. 与 v1 的关键区别

v1 (旧)v2 + Swarm (新)
角色固定 5 人 (PO/TL/Dev/QA/Ops)无角色,通用 Agent
流程固定状态机无状态机,任务树 + 蜂群自治
执行模式单 Agent 串行N Agent 蜂群并行,冗余攻击
通信全透明广播局部通信 + 痕迹标记 (Stigmergy)
共识民主投票涌现共识 (观察实际行为)
拓扑固定结构动态拓扑 (侦察/流水线/突击/守护)
工具预设列表自主发现、评估、获取
信息全透明广播Agent 自主搜索所需信息
错误重试 3 次/降级蜂群冗余并行 + 自主诊断修复
技术选型人类指定或民主投票蜂群分散调研,涌现最优
交付标准人类审查自动验证 + 验收报告
失败上报进入 BLOCKEDAgent 自主决定 escalate 或继续尝试
人机协作无,AI 孤岛运行主动求助人类:充值/密钥/决策/审批
文化/情绪人类社会模拟删除——过度设计,聚焦任务本身

12. 风险与应对

风险应对
AI 选错工具验证层把关 + 约束系统限制可选范围
AI 陷入循环任务级超时 + 预算上限强制退出
AI 生成不安全代码约束系统禁止危险操作 + 沙盒执行
验证标准不合理人类审查首次任务的验证定义,后续复用
成本不可控硬性预算上限,超支强制终止
产出质量不稳定硬性质量约束(覆盖率、测试通过),不通过不算完成

13. 实现路线图

Phase 0: 单 Agent 执行框架验证 (2 周) — 新增

目标: 验证单 Agent 能在隔离环境中稳定完成任务,不依赖蜂群机制。

核心问题
  • Agent 的执行环境(沙盒、权限)是否足够稳定?
  • 工具调用(文件读写、命令执行、搜索)是否可靠?
  • 验证框架能否捕获常见的失败模式?
  • 单 Agent 完成不同类型任务的成功率是多少?
任务清单
  • 沙盒容器环境搭建 (Docker)
  • Agent 执行引擎基础版 (执行 → 验证 → 上报结果)
  • 基础工具接口定义 (Tool Gateway)
  • 验证框架 v1 (文件存在、命令退出码 0、curl 返回 200)
  • 错误分类体系 (见第 14 章新增内容)
  • 状态持久化 (Agent 重启后恢复任务进度)
交付

验证单 Agent 能稳定完成以下 10 种不同类型任务,每种至少成功 3 次:

  1. 读取 CSV 文件并输出统计
  2. 编写一个 HTTP API 端点
  3. 修改现有代码文件中的 bug
  4. 编写单元测试(覆盖率 ≥ 60%)
  5. 搜索并理解一个陌生 API 的用法
  6. 在数据库中创建/查询/删除记录
  7. 写一个正则表达式处理文本
  8. 配置一个简单的 CI/CD 步骤
  9. 生成一个 README 文档
  10. 重构一个函数的代码风格

验收标准: 10/10 任务类型全部通过,单次任务成本控制在 $0.5 以内。


Phase 1: 单 Agent 自治 (2 周) — 修订交付物

原交付物"写一个 Python 脚本解析 CSV"过于简单,修订为实际意义的任务。

  • 任务提交 + 约束系统
  • 单 Agent 自主执行 (搜索 → 选工具 → 执行 → 验证)
  • 工具发现层 (扫描本地 Skills/MCP)
  • 基础验证框架 (文件存在、命令退出码 0)

交付: 能自主完成一个完整的 功能模块(如"用户注册模块:后端 API + 前端表单 + 数据库 Schema + 单元测试"),包含:

  • 可运行的代码
  • 测试覆盖率 ≥ 70%
  • 验证通过
  • 单次任务成本 ≤ $2.0

前置条件: Phase 0 验收通过后,方可进入 Phase 1。

Phase 2: 蜂群并行 (2 周)

  • 去中心化任务板 (Agent 自主认领)
  • 蜂群拆解 (3 Agent 同时多角度拆解,取最优)
  • 冗余并行执行 (同任务 2-3 Agent 同时做,取先成功)
  • 局部通信 + 痕迹标记 (Stigmergy)

交付: 3 Agent 蜂群并行完成 "Next.js 登录页面 + API + 数据库",提速 2x+

Phase 3: 蜂群智能 (2 周)

  • 动态拓扑 (侦察/流水线/突击/守护蜂群形态)
  • 涌现共识 (技术选型由实际行为自然收敛)
  • 蜂群诊断 (Bug 修复多路并行排查)
  • 成本权衡 (自动判断何时用蜂群、何时用单 Agent)

交付: 能自主决策 "这个任务值得派蜂群还是单兵"

Phase 4: 生产化 (2 周)

  • Web Dashboard (展示蜂群拓扑、Agent 状态、痕迹热图)
  • Git 集成 (蜂群并行分支自动合并)
  • CI/CD 触发 (GitHub Actions 自动跑验证)
  • 预算控制 (蜂群成本上限、自动降级为单 Agent)

交付: 人类在 Web 提交任务,蜂群自动并行攻击,监控面板实时可看,出 PR


14. 数据模型(完整版)

第 9 章是极简概念模型,本章是可直接用于建表的完整设计。

14.1 ER 关系图

┌─────────────┐       ┌─────────────┐       ┌─────────────┐
│   Mission1:NTaskN:1Agent     │
│  (任务批次)  │◄─────►│  (子任务)   │◄─────►│  (执行单元)  │
└──────┬──────┘       └──────┬──────┘       └─────────────┘
       │                     │
       │ 1:N1:N
       ▼                     ▼
┌─────────────┐       ┌─────────────┐
│ HumanTicket │       │StigmergyMark│
│ (人机协作票) │       │  (痕迹标记) │
└─────────────┘       └─────────────┘
       │                     │
       │ N:1N:1
       ▼                     ▼
┌─────────────┐       ┌─────────────┐
│  Swarm      │◄─────►│  SwarmAgent │
│  (蜂群实例)  │ 1:N   │ (蜂群成员)  │
└─────────────┘       └─────────────┘

14.2 表结构

mission — 任务批次
字段类型说明
idUUID PK任务唯一标识
descriptionTEXT人类输入的任务描述
constraintsJSONB完整约束对象(技术栈/预算/时间/质量)
acceptance_criteriaJSONB验收标准列表
statusVARCHAR(20)pending/decomposing/running/paused_human/completed/failed
swarm_modeVARCHAR(20)single/scout/pipeline/striker/guardian
budget_usdDECIMAL(10,4)预算上限
spent_usdDECIMAL(10,4)已消耗
started_atTIMESTAMP开始时间
completed_atTIMESTAMP完成时间
human_tickets_countINT产生的人机协作票数
result_summaryTEXTAI 自动生成的执行总结
task — 子任务
字段类型说明
idUUID PK子任务 ID
mission_idUUID FK → mission所属任务批次
parent_idUUID FK → task父任务(树形结构)
descriptionTEXT做什么
deliverableTEXT交付物定义
verification_typeVARCHAR(50)file_exists/command_exit_0/coverage_threshold/curl_200/e2e_pass
verification_commandTEXT验证命令
verification_expectedTEXT预期结果
statusVARCHAR(20)pending/claimed/running/paused_human/completed/failed/abandoned
claimed_byUUID FK → agent认领者
dependenciesUUID[]依赖的其他 task_id
estimated_cost_usdDECIMAL(10,4)预估成本
actual_cost_usdDECIMAL(10,4)实际成本
attemptsINT尝试次数
created_atTIMESTAMP创建时间
completed_atTIMESTAMP完成时间
error_logTEXT最后一次错误信息
agent — 执行单元
字段类型说明
idUUID PKAgent 唯一标识
statusVARCHAR(20)idle/running/waiting_human/error/terminated
capabilitiesJSONB{"react": 0.8, "sql": 0.6, "docker": 0.9}
current_task_idUUID FK → task当前执行任务
swarm_idUUID FK → swarm所属蜂群
model_tierVARCHAR(20)claude/gpt4o/gpt4o-mini(可动态降级)
lifetime_cost_usdDECIMAL(10,4)累计消耗
session_startTIMESTAMP本次会话开始
last_heartbeatTIMESTAMP最后心跳
ip_addressVARCHAR(50)沙盒容器 IP
container_idVARCHAR(100)Docker 容器 ID
swarm — 蜂群实例
字段类型说明
idUUID PK蜂群 ID
mission_idUUID FK → mission所属任务
topologyVARCHAR(20)scout/pipeline/striker/guardian
agent_countINTAgent 数量
sync_interval_secINT同步间隔
statusVARCHAR(20)forming/running/syncing/dissolved
formed_atTIMESTAMP组建时间
dissolved_atTIMESTAMP解散时间
swarm_agent — 蜂群成员关系
字段类型说明
swarm_idUUID FK → swarm蜂群 ID
agent_idUUID FK → agentAgent ID
role_in_swarmVARCHAR(20)explorer/builder/verifier/coordinator(动态角色)
joined_atTIMESTAMP加入时间
left_atTIMESTAMP离开时间
tasks_completedINT在蜂群中完成的任务数
PK: (swarm_id, agent_id)
human_ticket — 人机协作票
字段类型说明
idUUID PK票号
mission_idUUID FK → mission所属任务
task_idUUID FK → task触发此票的任务(可为空)
typeVARCHAR(20)api_key/recharge/decision/security_approval/info_request
titleTEXT标题
bodyTEXT详细说明(Markdown)
urgencyVARCHAR(20)low/medium/high/critical
statusVARCHAR(20)pending/notified/responded/resolved/expired
blocking_tasksUUID[]被阻塞的任务列表
action_typeVARCHAR(20)input/click/select/approve
input_schemaJSONB如果需要输入,定义字段
optionsTEXT[]如果是选择,提供选项
fallbackTEXT超时后的自动 fallback 行为
deadlineTIMESTAMP截止时间
responseJSONB人类的响应内容
responded_atTIMESTAMP响应时间
created_atTIMESTAMP创建时间
stigmergy_mark — 痕迹标记
字段类型说明
idUUID PK标记 ID
mission_idUUID FK → mission所属任务(全局痕迹可为空)
agent_idUUID FK → agent留下痕迹的 Agent
locationTEXT位置(文件路径/API/工具名)
typeVARCHAR(20)good_path/bad_path/caution/tip
contentTEXT痕迹内容
strengthDECIMAL(3,2)强度 0.0-1.0
decay_rateDECIMAL(3,2)衰减率(默认 0.9/小时)
created_atTIMESTAMP创建时间
expires_atTIMESTAMP过期时间
tool_catalog — 工具目录
字段类型说明
idUUID PK工具 ID
nameVARCHAR(100)工具名
sourceVARCHAR(20)skill/mcp/system/pypi/npm/github
install_specTEXT安装方式(pip install / npm install / git clone)
capabilitiesJSONB功能描述(LLM 可理解的语义)
usage_exampleTEXT使用示例
cost_per_callDECIMAL(10,6)单次调用成本
reliability_scoreDECIMAL(3,2)可靠性评分(0-1,基于历史)
last_used_atTIMESTAMP最后使用时间
success_rateDECIMAL(5,2)历史成功率(%)
execution_log — 执行日志
字段类型说明
idUUID PK日志 ID
mission_idUUID FK → mission所属任务
task_idUUID FK → task所属子任务
agent_idUUID FK → agent执行 Agent
levelVARCHAR(20)INFO/WARN/ERROR/OK/HUMAN
messageTEXT日志内容
cost_usdDECIMAL(10,6)本步消耗
tokens_inINT输入 token 数
tokens_outINT输出 token 数
modelVARCHAR(50)使用的模型
created_atTIMESTAMP时间戳

14.3 索引设计

-- 任务查询优化
CREATE INDEX idx_task_mission_status ON task(mission_id, status);
CREATE INDEX idx_task_claimed_by ON task(claimed_by) WHERE claimed_by IS NOT NULL;

-- 蜂群活跃查询
CREATE INDEX idx_agent_status_swarm ON agent(status, swarm_id);
CREATE INDEX idx_agent_heartbeat ON agent(last_heartbeat) WHERE status = 'running';

-- 人机协作
CREATE INDEX idx_ticket_status_deadline ON human_ticket(status, deadline) 
    WHERE status IN ('pending', 'notified');

-- 痕迹搜索
CREATE INDEX idx_mark_location ON stigmergy_mark(location);
CREATE INDEX idx_mark_mission_type ON stigmergy_mark(mission_id, type);

-- 日志时序
CREATE INDEX idx_log_mission_time ON execution_log(mission_id, created_at DESC);

15. 部署与运维架构

15.1 开发环境:Docker Compose

# docker-compose.dev.yml
version: "3.8"

services:
  api:
    build: .
    ports:
      - "8000:8000"
    environment:
      - DATABASE_URL=postgresql://aadev:aadev@postgres:5432/aadev
      - REDIS_URL=redis://redis:6379
      - LITELLM_PROXY_URL=http://litellm:4000
      - OPENAI_API_KEY=${OPENAI_API_KEY}
      - ANTHROPIC_API_KEY=${ANTHROPIC_API_KEY}
    volumes:
      - ./workspace:/app/workspace  # 代码产出挂载到宿主机
      - /var/run/docker.sock:/var/run/docker.sock  # Agent 启动沙盒容器
    depends_on:
      - postgres
      - redis
      - litellm

  dashboard:
    build: ./web
    ports:
      - "3000:3000"
    environment:
      - NEXT_PUBLIC_API_URL=http://localhost:8000

  postgres:
    image: postgres:16-alpine
    environment:
      POSTGRES_USER: aadev
      POSTGRES_PASSWORD: aadev
      POSTGRES_DB: aadev
    volumes:
      - pgdata:/var/lib/postgresql/data
    ports:
      - "5432:5432"

  redis:
    image: redis:7-alpine
    ports:
      - "6379:6379"

  litellm:
    image: ghcr.io/berriai/litellm:latest
    ports:
      - "4000:4000"
    environment:
      - LITELLM_MASTER_KEY=${LITELLM_MASTER_KEY}
    volumes:
      - ./litellm-config.yaml:/app/config.yaml
    command: ["--config", "/app/config.yaml"]

  # 可选:ChromaDB 用于向量检索(代码相似度)
  chroma:
    image: chromadb/chroma:latest
    ports:
      - "8001:8000"
    volumes:
      - chromadata:/chroma/chroma

volumes:
  pgdata:
  chromadata:

15.2 生产环境:Kubernetes

# k8s/namespace.yaml
apiVersion: v1
kind: Namespace
metadata:
  name: aadev

---
# k8s/api-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: aadev-api
  namespace: aadev
spec:
  replicas: 2  # API 无状态,可水平扩展
  selector:
    matchLabels:
      app: aadev-api
  template:
    metadata:
      labels:
        app: aadev-api
    spec:
      serviceAccountName: aadev-agent  # 允许启动沙盒 Pod
      containers:
      - name: api
        image: aadev/api:latest
        ports:
        - containerPort: 8000
        env:
        - name: DATABASE_URL
          valueFrom:
            secretKeyRef:
              name: aadev-secrets
              key: database-url
        - name: REDIS_URL
          valueFrom:
            configMapKeyRef:
              name: aadev-config
              key: redis-url
        volumeMounts:
        - name: docker-sock
          mountPath: /var/run/docker.sock  # 或配置 containerd
        resources:
          requests:
            memory: "512Mi"
            cpu: "500m"
          limits:
            memory: "2Gi"
            cpu: "2000m"
      volumes:
      - name: docker-sock
        hostPath:
          path: /var/run/docker.sock

---
# k8s/agent-sandbox.yaml
# Agent 沙盒以独立 Pod 运行,资源隔离
apiVersion: v1
kind: Pod
metadata:
  generateName: aadev-agent-
  namespace: aadev
spec:
  restartPolicy: Never
  containers:
  - name: agent
    image: aadev/agent-sandbox:latest
    resources:
      limits:
        memory: "1Gi"
        cpu: "1000m"
    securityContext:
      readOnlyRootFilesystem: true
      allowPrivilegeEscalation: false
      runAsNonRoot: true

15.3 监控体系

指标采集(Prometheus)
# prometheus.yml
scrape_configs:
  - job_name: 'aadev-api'
    static_configs:
      - targets: ['aadev-api:8000']
    metrics_path: /metrics
    scrape_interval: 15s

  - job_name: 'aadev-agents'
    kubernetes_sd_configs:
      - role: pod
        namespaces:
          names:
            - aadev
    relabel_configs:
      - source_labels: [__meta_kubernetes_pod_label_app]
        regex: aadev-agent
        action: keep
关键监控指标
指标类型告警阈值含义
aadev_mission_duration_secondsHistogramP99 > 2h任务执行时间
aadev_agent_cost_usdCounter单个 > $5/小时Agent 消费速度
aadev_budget_utilizationGauge> 80%预算使用率
aadev_task_failure_rateGauge> 30%任务失败率
aadev_human_ticket_pendingGauge> 5积压的人机协作票
aadev_agent_heartbeat_ageGauge> 5minAgent 心跳延迟
aadev_swarm_sync_durationHistogramP99 > 30s蜂群同步耗时
aadev_stigmergy_mark_countCounter痕迹标记数量
aadev_tool_call_latencyHistogramP99 > 10s工具调用延迟
Grafana 面板设计
┌─────────────────────────────────────────────────────────────────┐
│  🐝 AAT 蜂群监控 Dashboard                                       │
├─────────────────────────────────────────────────────────────────┤
│                                                                 │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐           │
│  │ 活跃任务  │ │ 活跃Agent │ │ 待处理   │ │ 今日消费  │           │
│  │   12     │ │   8/20   │ │  3 票   │ │  $47.3   │           │
│  └──────────┘ └──────────┘ └──────────┘ └──────────┘           │
│                                                                 │
│  蜂群拓扑实时图                                                   │
│  ┌─────────────────────────────────────────────────────────┐   │
│  │  [Mission-1284] 用户注册模块                              │   │
│  │                                                         │   │
│  │    ┌───┐      ┌───┐      ┌───┐                         │   │
│  │    │A-1│◄────►│A-2│◄────►│A-3Scout Swarm            │   │
│  │    └─┬─┘      └─┬─┘      └─┬─┘                         │   │
│  │      │ T1:doneT2:runT3:run                     │   │
│  │      ▼          ▼          ▼                            │   │
│  │    [DB表]    [API端点]  [邮件集成]                        │   │
│  │                                                         │   │
│  └─────────────────────────────────────────────────────────┘   │
│                                                                 │
│  任务流水线                                                      │
│  Mission-1284: ████████████░░░░ 67% ($3.2/$5.0)                  │
│    ├─ T1 设计数据库    [████████████done] $0.2                   │
│    ├─ T2 API实现       [████████░░░░run]  $0.8                   │
│    ├─ T3 邮件集成      [████████░░░░run]  $1.2 ⚠️ waiting_human  │
│    └─ T4 前端页面      [░░░░░░░░░░░░pend] $0.0                   │
│                                                                 │
│  成本趋势 (24h)                                                  │
│  $ ████████████████████░░░░░░░░░░ 峰值: $12.3 (14:00)            │
│                                                                 │
│  人机协作队列                                                    │
│  🔴 API Key 配置  |  15min前  |  阻塞2任务  |  [处理]            │
│  🟡 数据库选型    |  32min前  |  阻塞1任务  |  [处理]            │
│                                                                 │
└─────────────────────────────────────────────────────────────────┘

15.4 日志系统(Loki)

# 日志标签规范
# 所有 Agent 日志统一格式:
{
  "timestamp": "2026-05-08T14:32:01Z",
  "level": "INFO",
  "mission_id": "uuid",
  "task_id": "uuid",
  "agent_id": "A-3",
  "swarm_id": "uuid",
  "event": "tool_selected",
  "message": "选中 Resend 邮件服务",
  "cost_usd": 0.002,
  "tokens_in": 1200,
  "tokens_out": 350,
  "model": "claude-3-5-sonnet",
  "trace_id": "uuid"  # 分布式追踪
}

15.5 告警规则

# alertmanager-rules.yaml
groups:
  - name: aadev-budget
    rules:
      - alert: BudgetCritical
        expr: aadev_budget_utilization > 0.9
        for: 2m
        labels:
          severity: critical
        annotations:
          summary: "预算即将耗尽"
          description: "Mission {{ $labels.mission_id }} 预算使用率 {{ $value | humanizePercentage }}"

  - name: aadev-agent
    rules:
      - alert: AgentDown
        expr: aadev_agent_heartbeat_age > 300
        for: 1m
        labels:
          severity: warning
        annotations:
          summary: "Agent 心跳丢失"

  - name: aadev-human
    rules:
      - alert: HumanTicketStalled
        expr: aadev_human_ticket_pending > 0 <and> time() - human_ticket_created_at > 3600
        for: 5m
        labels:
          severity: warning
        annotations:
          summary: "人机协作票积压超过1小时"

15.6 运维 SOP

场景操作
API 额度耗尽Dashboard 自动触发 HumanTicket,同时降级到 gpt-4o-mini
Agent 沙盒崩溃K8s 自动重启 Pod,任务重新进入任务板
数据库连接池耗尽限制并发 Agent 数,自动扩容 Postgres 连接池
人类长时间未响应执行 fallback 策略(降级/跳过/免费替代方案)
蜂群分裂(Agent 失联)自动重分配任务到其他 Agent,标记失联 Agent 为 dead
磁盘满(代码产出)自动清理 7 天前的临时工作区,保留最终交付物

附录

A. 输入输出协议

// 人类输入
interface MissionInput {
  description: string;           // 自然语言任务描述
  constraints?: {
    tech_stack?: string[];        // 允许的技术栈
    budget_usd?: number;          // 预算上限
    time_limit_minutes?: number;  // 时间上限
    quality?: {
      min_test_coverage?: number;
      required_deliverables?: string[];
    };
    security?: {
      forbidden_operations?: string[];
      forbidden_paths?: string[];
    };
    scope?: {
      in?: string[];  // 必须包含
      out?: string[]; // 明确排除
    };
  };
}

// 系统输出
interface MissionResult {
  status: "completed" | "failed" | "escalated";
  tasks: TaskResult[];
  total_cost_usd: number;
  total_time_minutes: number;
  deliverables: {
    code_url?: string;
    test_report?: string;
    coverage_percent?: number;
    adr_documents?: string[];
  };
  execution_summary: string;  // AI 生成的执行总结
}

B. 目录结构

aadev-v2/
├── api/
│   ├── main.py              # FastAPI 入口
│   ├── missions.py          # 任务 API
│   └── verification.py      # 验证 API
├── core/
│   ├── decomposer.py        # 任务拆解
│   ├── controller.py        # Mission 控制器
│   └── verifier.py          # 验证引擎
├── agent/
│   ├── worker.py            # Agent 执行单元
│   ├── autonomy.py          # 自治协议
│   └── search.py            # 自主搜索
├── toolmesh/
│   ├── discovery.py         # 工具发现
│   ├── selector.py          # 工具选择
│   ├── acquisition.py       # 工具获取
│   └── gateway.py           # 统一网关 (MCP/Skills/System)
├── constraints/
│   └── enforcer.py          # 约束检查
├── sandbox/
│   └── docker_runner.py     # Docker 沙盒
├── web/
│   └── [Next.js Dashboard]
└── tests/
    └── e2e/

结语: v2 + Swarm 的核心是 "自治 + 并行涌现 + 人机协作"。人类只定义"要什么"和"不能做什么"。AI 蜂群自主决定"怎么做"、"谁来做"、"并行还是串行"。当遇到资金、密钥、决策、审批等必须人类介入的事,AI 会主动、清晰地求助,而非硬撑或静默失败。验证是唯一的硬契约——不通过就不算完成。蜂群用 2-3x 成本换 2-4x 速度,紧急任务全蜂群出击,简单任务单兵搞定。