贡献指南
本页是 AICodeReviewer 的公开贡献者指南,覆盖仓库布局、本地开发环境搭建、测试与验证矩阵,以及常见贡献工作流。仓库根目录的 AGENTS.md 持有常驻规则、护栏、环境说明,以及需要避免重新引入的已知代码陷阱列表——较大改动前请先阅读。
| 路径 | 用途 |
|---|---|
packages/* |
运行时 TypeScript 包(CLI、core、server、agents、sandbox、outputs、mcp-output、llm、vcs、store、eval)。用 pnpm workspace 和 TypeScript project references 管理。 |
docs/site |
本文档站点(Astro Starlight,English + 简体中文)。独立的 workspace 包,不属于运行时。 |
docs/(其他) |
专题参考模块(如输出通道),编写本站页面时参考。 |
example/ |
部署样例:config.yaml、.env.sample、Compose 栈、trigger 脚本。 |
deploy/ |
Dockerfile、deploy.sh 及相关部署资产。 |
eval/ |
永久 eval CLI 测试 fixture。 |
AGENTS.md |
常驻贡献者指引、护栏和已知代码陷阱。 |
.agents/skills/ |
可复用的工作流技能(审计、部署、维护等)。 |
开发环境搭建
Section titled “开发环境搭建”要求:
- AICR runtime 使用 Node.js
>= 22(better-sqlite313 的硬性要求;部署镜像 使用 Node 24 LTS userspace)。 docs:build/docs:check使用 Node.js>= 23.6;源码配置校验器依赖 Node 原生 TypeScript stripping。文档 CI job 使用 Node 24。- pnpm。
# 在仓库根目录pnpm installpnpm build测试与验证矩阵
Section titled “测试与验证矩阵”最后一次修改后、提交变更前运行全部适用门禁,并确认工具实际发现了预期文件或测试。Linux/CI 的最终 runtime 门禁是 pnpm run ci;Windows PowerShell 直接调用 Node 二进制。
| 步骤 | Linux/CI | Windows PowerShell |
|---|---|---|
| ESLint | pnpm lint |
node node_modules/eslint/bin/eslint.js . --max-warnings=0 |
| 类型检查 | pnpm typecheck |
node node_modules/typescript/bin/tsc -b tsconfig.json --pretty false |
| 单元测试 | pnpm test |
node node_modules/vitest/vitest.mjs run --coverage |
| Markdown lint | pnpm markdownlint |
node node_modules/markdownlint-cli2/markdownlint-cli2-bin.mjs |
| 构建 | pnpm build |
cmd /c "pnpm build" |
| Eval fixture 校验 | pnpm eval:validate(构建后) |
node packages/cli/dist/index.js eval --validate-only |
| 文档构建 | pnpm docs:build |
pnpm docs:build |
pnpm eval:validate 运行 aicr eval --validate-only,只校验 eval/*.json 的结构和预期 problem 约定——不需要 LLM,不需要 config 密钥。完整 aicr eval 会加载 config 并调用 LLM,应作为单独的、按环境配置的 benchmark 任务。
影响配置 shape、agent 适配器、MCP 工具接口约定、输出渲染、部署行为或公开工作流的变更,必须在同一次变更中更新对应文档、example/config.yaml 和 example/README.md。
本地服务集成测试
Section titled “本地服务集成测试”以下测试可使用本机临时服务,无需生产凭据:
| 变量 | 要求与覆盖范围 |
|---|---|
AICR_SVN_TEST_EXECUTABLE |
svn 的绝对路径,同目录提供 svnadmin 和 svnserve。启用真实仓库元数据测试,以及 post-commit hook → 带认证 HTTP → SQLite 调度测试。 |
AICR_REDIS_TEST_URL |
本机测试 Redis 的 URL。启用自动提交存储和模型目录持久化测试;目录测试使用独立随机键前缀。 |
AICR_GITEA_TEST_URL / AICR_GITEA_TEST_TOKEN |
一次性回环 HTTP Gitea 及临时管理员 token。测试创建私有仓库和用户、发布 issue,再读取持久化的 assignees。两者都未设置才跳过,配置不完整则失败。 |
运行上面的测试命令前设置变量;未设置时,对应集成测试会跳过。SVN fixture 位于 build/tmp/,hook 测试会停止自己启动的服务。这些测试不调用 LLM,也不向远端系统发布 review;部署专属的认证和网络仍需单独验收。
Gitea 验收在 Linux 或 WSL Debian 的仓库根目录运行,需有 rootless Podman、curl、node 和 timeout:
bash tests/services/with-gitea.sh \ pnpm exec vitest run packages/outputs/test/gitea-assignment-live.test.ts --maxWorkers=1脚本固定 Gitea 1.25.4 与 SQLite,限制 1 CPU / 512 MiB,绑定随机回环端口。
它在 ~/workspace/github/atframework 下创建独立目录(可用 AICR_ACCEPTANCE_ROOT
覆盖),提供两个 fixture 变量,退出时移除自己的容器、数据及本轮下载的镜像。
服务另设 900 秒运行上限。日志保留在 build/logs/gitea-*。
中断后仍须检查自有资源已清理;SIGKILL 无法执行目录清理。这些结果只覆盖固定 Gitea 版本。
packages/core/test/config-examples.test.ts 始终校验部署配置及仓库文档的配置 YAML
片段,包含两种语言;畸形配置片段明确失败,不会被跳过。
SVN 脚本使用固定 Debian 镜像和 Subversion 1.14.5-3,限额 1 CPU / 256 MiB,
回环随机端口,采用同样的 900 秒生命周期和清理规则。脚本提供 AICR_SVN_TEST_URL;
测试进程的 PATH 需有 svn。用例核验辅助仓库内容、diff 与失败清理,
并通过 orchestrator 和确定性模型 fixture 执行分析与发布。
bash tests/services/with-svn.sh \ pnpm exec vitest run packages/vcs/test/svn-context-live.test.ts \ packages/server/test/svn-analysis-live.test.ts --maxWorkers=1PostgreSQL SCRAM/TLS/角色、Redis TLS/ACL/AOF 与 SVN HTTPS/authz/hook 使用部署 fixture。
它在容器重启后核验持久化数据,使用随机回环端口,服务共享 1 CPU / 512 MiB。
退出时删除自有容器、数据卷和临时目录,Debian 包版本记录在
build/logs/deployment-versions.log。
bash tests/services/with-deployment-services.sh可选子命令接收 AICR_PG_TEST_URL、AICR_REDIS_TEST_URL、
AICR_REDIS_OOM_TEST_URL 和 NODE_EXTRA_CA_CERTS。证书验证保持开启,
OOM 注入使用独立 Redis 进程;共享 PG 的测试串行执行:
bash tests/services/with-deployment-services.sh \ pnpm exec vitest run --coverage --maxWorkers=1按需启用真实账户
Section titled “按需启用真实账户”真实账户测试在整组环境变量缺省时跳过,配置不完整时失败,不会自动读取凭据文件。 请使用测试群和测试账户。
| 必需变量 | 用例与可选设置 |
|---|---|
AICR_FEISHU_TEST_APP_ID、AICR_FEISHU_TEST_APP_SECRET、AICR_FEISHU_TEST_RECEIVE_ID |
packages/outputs/test/feishu-app-live.test.ts:读取成员/资料,发送一张卡片并撤回。AICR_FEISHU_TEST_DIRECTORY_CHAT_ID 选择另一来源群;AICR_FEISHU_TEST_MENTION_OPEN_ID 启用对一个获准成员的通知。 |
AICR_ZHIPU_TEST_BASE_URL、AICR_ZHIPU_TEST_API_KEY |
packages/llm/test/providers-live.test.ts:glm-5.3-flash;AICR_ZHIPU_TEST_KIND 选择 openai_compatible(默认)或 anthropic。 |
AICR_KIMI_TEST_BASE_URL、AICR_KIMI_TEST_API_KEY |
同一用例,kimi-for-coding;AICR_KIMI_TEST_KIND 选择协议。 |
anthropic 的 base URL 填写协议根地址,不带 /v1。
LLM 每个已启用供应商调用一次,60 秒截止、256 输出 token、关闭 thinking、无自动重试。
测试核验回答与 usage,不衡量评审质量或计费。日志只记录数量和 usage,
不记录凭据、成员资料或供应商原始错误。飞书撤回失败则测试失败;强制中断后需核对测试群
是否仍有测试卡片。
维护了 development/secret/secret.yaml 时,可显式调用本地 helper,需 yq v4;
它只将选定字段读入测试子进程环境:
node tests/services/with-local-secrets.mjs feishunode tests/services/with-local-secrets.mjs zhipunode tests/services/with-local-secrets.mjs kiminode tests/services/with-local-secrets.mjs zhipu anthropicnode tests/services/with-local-secrets.mjs kimi anthropic字段组为 .channel.feishu_app.{app_id,app_secret,receive_id}、
.llm.provider.zhipu.{baseURL,token} 与
.llm.provider.kimi_coding_backup.{baseURL,token}。CI 直接提供环境变量。
这些真实调用与普通覆盖率测试分开执行。
新增 package
Section titled “新增 package”- 在
packages/<name>/下创建包目录,包含自己的package.json、tsconfig.json、src/和test/。 - 把包加入
pnpm-workspace.yaml(workspace 已 globpackages/*,通常自动包含)。 - 从根
tsconfig.json和任何消费它的包加 TypeScript project reference;并从新包的tsconfig.json反向引用其依赖。 - 至少加一个
test/index.test.ts,让包有测试面,即使只导出一个常量。 - 如果包引入了原生模块,把新的
onlyBuiltDependencies条目加入pnpm-workspace.yaml(pnpm 10 用onlyBuiltDependencies门控原生构建)。
新增或修改配置字段
Section titled “新增或修改配置字段”packages/core/src/config.ts 中的 Zod schema 是真源。
- 更新 schema(以及任何
superRefine跨字段校验)。 - 在
packages/core/test/config.test.ts加或更新测试。 - 在
example/config.yaml加带注释的示例。 - 更新
docs/site/src/content/docs/.../configuration/下相关叙述页,以及配置字段参考中的字段表——两个 locale 都要改。字段表漏掉 schema 字段、写了不存在的字段、或中英两表漂移时,pnpm docs:build会直接失败并指出缺什么。 - 如果字段改变运行时行为,更新
example/README.md和对应专题文档。
workspace 配置文件不能写系统级字段;遵守 cache / defaults / instances 三段式 shape 和 global → workspace-default → workspace-instance 的覆盖顺序。
新增输出通道
Section titled “新增输出通道”- 在
packages/outputs/src/实现 dispatcher,并在输出注册表中注册。channelkind是受注册表约束的自由字符串(不是封闭枚举)。 - 在模板引擎下为 problem 和 summary 变体加内置 Handlebars 模板。
- 加测试;如果 channel 是 IM bot,还要加 IM-markdown 转换器测试(表格正则不能在
.test()上用gflag)。 - 在输出通道文档化该 channel,并把字段加进配置字段参考。
- 在
example/config.yaml加带注释的示例。
每个 channel 必须遵守的 problem schema、summary schema、channel 映射和 no-problems 策略,参见输出通道。
维护文档站点
Section titled “维护文档站点”文档站点是双语的(English 在 .../en/,简体中文 在 .../zh-cn/)。每个面向用户的页面都同时存在于两个 locale;请保持配置键、命令、路径、字段名和枚举值在不同 locale 间完全一致。
- 用
pnpm docs:build本地构建并校验。构建会依次运行六道校验:公开/内部边界(src/content/docs/下的页面不得引用内部 AI/路线图文档树,也不得保留仅供维护者参考的迁移占记)、配置字段表对 Zod schema 的覆盖、CLI 命令/flag 与packages/cli实现的一致性、内部链接/锚点解析(含 sidebar 覆盖)、SEO 元数据(每个页面都需要非空且长度合规的title/description,以及已提交的robots.txt和 1200x630og-image.png)、双语一致性(两个 locale 页面集合相同、代码块数量与机器 token——配置键、环境变量、flag、路径——一致,且不出现禁用填充词)。 - sidebar slug 省略
index段(如troubleshooting/index.md的 slug 是troubleshooting)。frontmattertemplate只接受doc或splash;Starlightsocial是链接项数组。 - 内容页用
.md。两个首页(en/index.mdx、zh-cn/index.mdx)用.mdx,以便渲染 Starlight 组件(hero frontmatter 加Card、CardGrid、LinkCard、Steps、Aside)。MDX 由 Starlight 内置提供,无需额外集成;组件在纯.md中不会渲染。公开内容校验器同时扫描.md和.mdx。 - 交叉链接使用带 locale 前缀的路径(
/en/...、/zh-cn/...)。
当你改变配置 shape、输出渠道规范或运行时行为时,请在同一次变更中更新两个 locale 的相关页面。
- 保持编辑最小且外科手术式;不要为了通过而削弱 lint、类型检查、测试或 markdown 门控。
- 所有临时任务产物(草稿脚本、调试日志、一次性报告、benchmark 输出)都放在
build/下,绝不放在仓库根目录、eval/或任何包目录。 - 公共/共享模块(
packages/cli/src、ReviewEvent、模板上下文)必须保持平台中立——从@aicr/core导入规范 schema/常量,把 provider/channel 专属名称限制在配置约定、文档、测试和平台专属适配器内。
完整、常驻的贡献者规则——包括需要避免重新引入的已知代码陷阱编号列表——请阅读仓库根目录的 AGENTS.md。