7.7 KiB
AGENTS.md
Codex / AI coding agent 的仓库级入口。进入本仓库后先读本文,再进入
docs/00-ai-start-here.md。
项目定位
cmbuyer 是一个自动化采购系统:采购服务(网页端,admin/,Go)负责建单与人工决策,
采购工具(Windows 桌面端,client/,Python)驱动 Android 手机在拼多多完成找货和下单。
系统只创建待付款订单,任何情况下都不自动付款。
当前状态:两端骨架、基础模型、登录和真机取证脚手架已落地;Phase 1 真机取证与不依赖页面判据的
Phase 2 服务端任务并行。实时快照见 docs/current-state.md。
必读顺序
- 本文。
docs/00-ai-start-here.md:入口流程与四条特有纪律。docs/05-coding-rules.md:第 1 节红线。docs/current-state.md:当前代码现实与下一步任务。- 与当前任务相关的具体文档(按
docs/agent-context.json路由)。
日常会话按 agent-context.json 的 bootstrap.always_read 与任务类型 routes 读取,
不机械重读全部文档。
四条不可协商的规则
1. 不碰钱
绝不编写点击支付、免密支付、先用后付或任何扣款控件的代码。 这条没有例外,也不接受「先做个开关默认关掉」。
系统会点击「提交订单」创建待付款订单,但必须满足四个前置条件(授权未消费且服务端 提交围栏已建立、闸门二通过、闸门三通过、控件唯一),且只点一次、点击后无论结果 都不重试。围栏申请失败或响应不明时不得点击;围栏建立后只能调和同一提交记录。 管理员点击“开始采购(只创建待付款订单)”是唯一的人类授权动作。T-103 的规格选择/读价隔离 验证路径不得引用数量、确认页、提交或付款函数;后续能力必须按真机取证任务逐段开放,并有静态 调用链测试证明未获准能力不可达。
2. 安全边界只能收紧
docs/04-architecture.md 第四节列出全部硬约束,含三道价格
闸门与提交订单四条件。不得在任务中放宽任何一条,包括为了让流程跑通而临时放宽。
确需变更时先改架构文档并说明理由。
价格只在规格面板和订单确认页读。别处读不到就转人工,不用其他位置的数字凑合。
3. 页面判据必须先真机取证
拼多多 App 会随版本改变页面结构。不得从前序项目、旧文档或推理直接写判据。 必须先真机 dump 取证,把截图路径、XML 路径和拼多多 App 版本写进任务文件。
4. 真机验收只能由人完成
needs_device: true 的任务,agent 不得自行标 DONE,保持 DOING 并写明等待事项。
前序项目的地位
/mnt/d/chengma/cmroubao 与 /mnt/d/chengma/cmpdd 是本项目的设计依据,不是事实来源。
- 可以参考它们的结构决策和护栏理由。
- 不得把它们的页面判据、常量或结论当作已验证事实直接使用。
- 引用其中任何结论时,必须在本项目重新验证并记录证据。
搬运护栏时,必须连同理由一起搬。只搬代码不搬理由,后人会把它当碍事的逻辑删掉。
工作模式
- 默认单任务、单责任 agent、单写入者:一个任务只有一个负责人,同时只有一个 agent
修改该任务的
write_paths。 - 多 agent 并行只拆到写路径互不重叠的任务。
admin/采购服务与client/采购工具天然可并行。 这条不再只靠自觉:scripts/validate_agent_context.py会拒绝两个DOING任务写同一路径。 - 共享文档只由任务所有者写入。
docs/agent-context.json的shared_documents列出 跨任务共享的文档;受托执行者不得直接改它们,只提交建议由所有者合入。共享文档可以出现在 某个任务的write_paths,但必须逐条显式列出,不得用通配圈走。 - 复杂任务先规划再编码。方案、不可变约束、写路径和验收门禁必须写入任务文件, 不能只停留在对话里。
- 任务内委派不是默认流程。委派后仍保持唯一写入者,执行者必须继承任务文件中的不可变 约束与验证要求。
- 无论是否委派,任务所有者都对结果负责,独立审阅差异、重跑验证; 不能把执行者或工具的自我报告当成完成证据。
任务状态存放在哪
任务的叙述性内容(标题、标签、依赖、方案正文、验收要点、执行记录)权威在自建 Vikunja 的
cmbuyer 项目;docs/tasks/T-XXX.md 里两行 VIKUNJA EXPORT 标记之间的内容是它的
单向投影,由 scripts/vikunja_export.py 覆盖写入,不要手工编辑。
以下四项的权威始终在 git,不迁往 Vikunja:
| 项 | 位置 | 为什么不能搬 |
|---|---|---|
status |
frontmatter | 门禁靠它判定谁能写哪些路径,且必须离线可跑;权威在远端等于校验要联网 |
write_paths |
frontmatter | 同上,是并行安全的判定输入 |
context_ref / work_branch |
frontmatter | 锚定 commit,离开 git 就失去意义 |
## 边界与安全边界条目 |
正文区块外 | 见本文第 2 条:能否收紧靠 git diff 逐条复核 |
安全边界的权威一旦搬到远端,放宽边界的改动在 diff 里只呈现为「导出内容更新」,
审计链就断了。status 同理:它不是看板装饰,是决定并行写入安全的协调契约,
每次变更都应当产生一个 commit。
Vikunja 的 bucket 与 done 标志是人类视图,不是判定依据。两者不一致时以 git 为准;
scripts/vikunja_export.py 会在导出时只读比对并提示漂移,但不会反向写回。
只读任务内容不需要接入 Vikunja——导出产物就在仓库里,git clone 即可。只有写状态和
执行记录才需要配置 MCP。
各家 agent 指向同一个包装脚本,不要各写各的:
// Claude Code:仓库内 .mcp.json(已配置,无需重复)
{ "mcpServers": { "vikunja": { "type": "stdio", "command": "./scripts/vikunja-mcp.sh" } } }
# Codex CLI:~/.codex/config.toml
[mcp_servers.vikunja]
command = "/mnt/d/chengma/cmbuyer/scripts/vikunja-mcp.sh"
任何配置都不得内联凭据。 脚本自己按 $VIKUNJA_ENV_FILE → 仓库根 vikunja.env →
家目录的顺序读取,token 只存在于 vikunja.env(已 gitignore,样例见 vikunja.env.example)。
把 token 写进 agent 配置文件等于把它复制到一个没人在看的地方。
Vikunja 不可达时按 degraded_mode 处理:继续手头任务,不领新任务,不写远端。
验证
按 docs/03-tech-stack.md 第六节的验证矩阵判断层级:
# 采购服务(admin/)
go test ./...
go vet ./...
# 采购工具(client/)
python -m unittest discover -s tests -t .
python -m compileall -q src tests
# 上下文清单
python scripts/validate_agent_context.py
跨端契约改动必跑完整门禁——两端会同时坏。
两端已初始化;跨端契约改动还需在仓库根运行 ./init.ps1(或 ./init.sh)完成安装、测试、
vet/build、compileall 和上下文门禁。
风格
- 文档与 UI 文案使用中文,标识符使用英文。
- 金额一律用十进制字符串,不用浮点数。
- 护栏必须连同理由一起注释。
- 内容面向执行,每条规则能落到「读取什么、修改什么、验证什么」。