CodeWhale 贡献者开发指南:本地验证门禁、快速迭代循环与 PR 落地(Harvest)流程
CodeWhale 是一个用 Rust 编写的终端编码 Agent,本仓库的 CONTRIBUTING.md 不仅是一份贡献规范,更是一套可执行的开发工程手册:它规定了从 Rust 1.88+ 环境搭建、fmt/clippy/test 三级验证门禁,到 nextest 加速的本地快速循环、低内存机器构建配方、多 worktree 构建缓存隔离的完整做法,并详细说明了 PR 如何以“直接合并”或“Harvest(收割)”两种路径落地、贡献者署名如何被机器可读取地保留。读完本文,你能够按仓库实际门禁独立跑通一条完整的贡献流水线:本地修改 → 快速局部验证 → 全量权威门禁 → 提交符合署名规范的 PR。
环境要求与开发环境搭建
CodeWhale 贡献工作的第一道门槛是工具链。CONTRIBUTING.md 列出的前置条件为:
- Rust 1.88 或更高版本(edition 2024)
- Cargo 包管理器
- Git
这一要求不是随意设定的。Cargo.toml 中可以看到工作区级别声明了 edition = "2024"、rust-version = "1.88",并且注释说明了原因:Rust 1.88 稳定了 if/while 条件中的 let_chains,代码库大量依赖这一特性,通过 rust-version 字段让旧工具链的用户得到清晰的“package requires rustc 1.88+”报错,而不是难以理解的 E0658 错误。此外,rust-toolchain.toml 将工具链固定在 stable 通道。
环境搭建步骤:
# 1. Fork 仓库后克隆你自己的 fork
git clone https://gitcode.com/GitHub_Trending/de/Codewhale
cd CodeWhale
# 2. 构建项目
cargo build
# 3. 运行全部测试
cargo test --workspace --all-features
# 4. 以开发配置运行
cargo run --bin codewhale
注意第 4 步的 --bin codewhale:它指向的是 crates/cli 中的二进制(codewhale-cli crate 声明了 [[bin]] name = "codewhale",入口为 crates/cli/src/main.rs),即分发器门面(dispatcher facade),而不是 crates/tui 中的交互式 TUI 二进制 codewhale-tui。这一点在后文“工作区结构”一节还会展开。
代码风格与测试放置规范
代码风格
- 提交前运行
cargo fmt保证格式一致 - 运行
cargo clippy并处理所有警告 - 遵循 Rust 命名约定(函数/变量用 snake_case,类型用 CamelCase)
- 为公共 API 添加文档注释
工作区在 Cargo.toml 中用 [workspace.lints.rust] 的 warnings = "deny" 固化了“CI 已通过 RUSTFLAGS: -Dwarnings 执行的策略”,成员 crate 通过 [lints] workspace = true 选择加入。也就是说,普通的 cargo check(不带额外参数)就与 CI 的警告门禁一致,这不是文档约定,而是写进 manifest 的机制。
测试放置
- 为新功能编写测试
- 确保既有测试全部通过:
cargo test --workspace --all-features - 单元测试与被测代码同置(标准 Rust
#[cfg(test)]模块),集成测试放在所属 crate 的tests/目录下(例如crates/tui/tests/或crates/state/tests/) - 仓库根目录的
tests/目录不被使用
最后一条是明确的反模式警告:不要往仓库根放测试,每个 crate 自管自己的测试资产。
Push 前的验证门禁
这是贡献文档中最硬核的部分:每次 push 之前必须运行以下命令,它们与 CI 在 PR 上强制执行的内容一致——本地通过意味着 PR 的各验证通道(lane)也应当通过:
cargo fmt --all -- --check
cargo clippy --workspace --all-features --locked -- \
-D warnings \
-A clippy::uninlined_format_args \
-A clippy::too_many_arguments \
-A clippy::unnecessary_map_or \
-A clippy::collapsible_if \
-A clippy::assertions_on_constants
cargo test --workspace --all-features --locked
三条命令的含义:
cargo fmt --all -- --check:只检查不重写,作为门禁时任何格式偏差都会导致失败。cargo clippy ... -D warnings:把所有警告提升为错误,但同时用-A放行五个既有噪音较多的 lint(uninlined_format_args、too_many_arguments、unnecessary_map_or、collapsible_if、assertions_on_constants)——这个放行清单是 CI 的真实配置,照抄即可,无需自己猜测。cargo test --workspace --all-features --locked:全特性、锁定依赖图的全量测试,是权威(authoritative)测试门禁。
Release lane 的更严格 clippy
Release 通道运行更严格的 clippy:额外加 --all-targets,把 test、bench、example 目标也纳入 lint。文档特别提醒:只跑 --all-features 会漏掉一些在 release 通道才会失败的 lint,因此在请求 review 或做 release 相关工作之前,应使用这个更完整的形态:
cargo clippy --workspace --all-targets --all-features --locked -- \
-D warnings \
-A clippy::uninlined_format_args \
-A clippy::too_many_arguments \
-A clippy::unnecessary_map_or \
-A clippy::collapsible_if \
-A clippy::assertions_on_constants
这一点也被固化进了 PR 模板:.github/PULL_REQUEST_TEMPLATE.md 的 Testing 部分要求勾选 cargo fmt --all -- --check、cargo clippy --workspace --all-targets --all-features --locked(在 CI 放行清单下无警告)、cargo test --workspace --all-features --locked 三项,并在注释中指明“准确的门禁命令(含 clippy 放行清单)见 CONTRIBUTING.md 的 Pre-push verification”。Checklist 里还有一条值得注意:“Harvested/co-authored credit uses a GitHub numeric noreply address”——署名地址格式是模板级检查项,后文会解释为什么。
快速本地循环:dev-cargo / dev-test 脚本与 nextest
上面那套全量门禁是 CI 的标准,但不是每次编辑都需要它。文档给出的理由很直白:crates/tui 是一个约 75 万行的巨型 crate(当前对 crates/tui/src 的实测已经约 85.7 万行),保持循环速度的关键在于“不要不必要地重复构建它”。完整的数字与推理在 docs/BUILD_PERFORMANCE.md 中。推荐的快速循环:
# 1. 先做类型检查(首次构建后只需几秒;无 codegen、无链接)
scripts/dev-cargo.sh check -p codewhale-tui
# 2. 只跑改动附近的测试(一个 crate、一个 filter)
scripts/dev-test.sh tui fleet_setup
# 或者按源文件映射:
scripts/dev-test.sh crates/tui/src/elapsed.rs
# 3. 跑整个 crate 的单测套件。scripts/dev-test.sh 在已安装 nextest 时
# 会使用 nextest(每个测试一个进程、所有核心占满、慢测试点名;
# 约 100 秒 vs libtest 的约 270 秒)。
cargo install cargo-nextest --locked # 只需一次
scripts/dev-test.sh tui
scripts/dev-cargo.sh nextest run --workspace --all-features --locked
# 4. Push 前,按 CI 的方式跑权威门禁:
cargo test --workspace --all-features --locked
dev-cargo.sh / dev-test.sh 到底做了什么
两个脚本都是 /bin/sh 实现,可以查看源码确认行为:
- scripts/dev-cargo.sh 是“日常编译入口”。它 source 了
scripts/dev-cache.sh应用可移植缓存拓扑(下文详述),并额外导出RUST_MIN_STACK=16777216——注释说明这是为了匹配 CI 和产品端的 16 MiB 属主线程栈,避免本地cargo test/nextest 在默认约 2 MiB(Windows 约 1 MiB)栈上直接 abort。 - scripts/dev-test.sh 把“工作区区域或源文件路径”映射为最快的 cargo/nextest 调用。运行
scripts/dev-test.sh --list可以看到完整的区域表:agent、app-server、cli、config、core、state、tui等每个区域对应一条cargo test -p codewhale-<crate> --lib --locked;crates/tui/src/下的子目录还会进一步映射到tui::、tools::、core::、commands::等过滤前缀,crates/tui/tests/integration/映射到tui-integration区域。当cargo-nextest在 PATH 上时,运行阶段自动换成cargo nextest run(同二进制、每测试一进程);用CODEWHALE_DEV_NEXTEST=0可强制回退到 libtest。
nextest 配置与权威门禁的关系
.config/nextest.toml 已经处理了并行带来的竞争问题,因此对全工作区直接 cargo nextest run 是安全的。查看 .config/nextest.toml 可以看到关键配置:
slow-timeout = { period = "30s" }:超过 30 秒的测试被点名,贡献者能看到时间去向;retries = 0、fail-fast = false:flaky 测试被视为 bug 报告而不是要掩盖的东西;- 三个 test-group 用于约束会竞争外部资源的集成测试:
spawns-binaries(拉起真实codewhale二进制、等待服务启动截止的测试,max-threads = 3)、telemetry-contract(遥测契约测试,max-threads = 1,因为其 fixture 的进程内互斥锁无法序列化 nextest 的每测试一进程 worker)、exec-persistent-service(等待真实子进程 pid 文件的测试,并行负载下文件迟迟不出现,max-threads = 1串行执行,注释明确“串行它们;不要丢弃这些测试”)。
文档同时划清了边界:nextest 不运行 doctest,权威的 cargo test 门禁才运行;且测试不得依赖“与另一个测试在同一进程运行”这一假设(nextest 给每个测试独立进程);如果某个测试需要 rustls 加密 provider,应像生产启动时那样在该测试内自行安装。
低内存机器与交叉编译构建
在小于 16 GB 内存的机器上(或交叉编译,例如面向 OHOS),文档要求一次只跑一个 rustc:
- 设置
CARGO_BUILD_JOBS=1(或-j1) - 一次只构建一个 crate
- 测试用
--lib,绝不用--workspace/--all-targets
文档给出的内存数字:tui 库自身的 rustc 需要约 6 GB,其单元测试构建约 8 GB;而 cargo test --workspace 会把两者同时调度——这正是社区成员在 Windows 上为 OHOS 交叉编译时报告的“两个各约 4 GB 的 rustc 进程”形态(RSS 统计因 OS 而异,但形态相同)。
docs/BUILD_PERFORMANCE.md 的 “Low-memory build recipe (machines with < 16 GB, cross-builds)” 一节给出了完整配方:
# 一次一个 rustc:tui lib 与其单元测试构建不再重叠
export CARGO_BUILD_JOBS=1 # 或: cargo build -j1 ...
# 只构建你正在工作的 crate,且只构建其库:
cargo build -p codewhale-tui
cargo test -p codewhale-tui --lib -- <filter>
# 小机器上不要用 --workspace/--all-targets;一次一个 crate
# (scripts/dev-test.sh <area> 会挑选最窄的命令)
# 可选:如果 8 GB 的单元测试构建仍然太多(更慢):
export CARGO_PROFILE_DEV_CODEGEN_UNITS=4 # 峰值约 6 GB,墙钟时间约 +40%
# 交叉构建(如 OHOS)继承同样数字:给 cargo/ohrs 调用加 -j1,
# 构建 release profile——它不带测试模块,峰值低于单元测试构建
多 worktree 的构建缓存隔离
在多个 worktree 中工作时,不要默认共享同一个 CARGO_TARGET_DIR:两个 cargo 会在同一个 target 上 flock 并相互串行化。文档指出的解决方案是 scripts/dev-cargo.sh / scripts/dev-test.sh,它们让每个工作区拥有自己的 Cargo build-dir——位于 ${CODEWHALE_CACHE_ROOT:-${XDG_CACHE_HOME:-$HOME/.cache}/codewhale} 之下的 {workspace-path-hash} 子目录。
读取 scripts/dev-cache.sh 可以确认这套拓扑的完整语义:
- 缓存根默认是
${XDG_CACHE_HOME:-$HOME/.cache}/codewhale,可用CODEWHALE_CACHE_ROOT覆盖(没有机器专属默认值); CODEWHALE_DEV_CACHE控制模式:auto/1/force走隔离 build-dir,local保留./target,0什么都不做;CODEWHALE_DEV_CACHE=local即文档所说的“想留在./target时”的开关;- Cargo 1.91 之前回退到 per-workspace 的
CARGO_TARGET_DIR指纹目录,1.91+ 使用build.build-dir与{workspace-path-hash}模板; sccache仅在增量编译已关闭(CARGO_INCREMENTAL=0或CODEWHALE_SCCACHE=1)且sccache在 PATH 上时才包装 rustc——“缺失的二进制是打印出来的回退,不是错误”;- 脚本还会检查缓存卷的剩余空间:冷构建 build-dir 约 6 GB,低于 15 GiB(阈值可用
CODEWHALE_DEV_CACHE_MIN_FREE_GIB调整)会在构建开始前告警,而不是构建失败后才发现。
文档还给出一个例外:单一共享 CARGO_TARGET_DIR 仅对串行化的 trunk 工作有效。
平台绑定检查与本地 git hooks
有些检查是平台绑定的,或有意排除在普通变更之外。文档的建议是“按它们回答的风险来选择,而不是把每个可用套件都当作仪式”:
- TUI 可见行为在真实终端中按受影响的尺寸与交互路径验收。原来的全屏 PTY 断言套件已被移除——它冻结了布局与文案,却遗漏了产品质量。
- 长时间运行的进程验收应使用密封的本地 home、本地 fixture 和真实二进制;记录终端尺寸、输入、可见结果与任何文件系统副作用,而不是再加全屏 golden 文件。
- OCR(
image_ocr)使用 macOS Vision 框架或本地安装的tesseract;其平台特定路径以cfg(target_os = "macos")门控并依赖宿主工具。 - Seatbelt 沙箱测试仅在 macOS 运行(模块级
cfg(target_os = "macos"))。
本地 git hooks 是可选的
本仓库不安装 git hooks,也不存在 hook 安装器;CI 才是被强制的门禁。如果你想要一个运行上述命令的本地 pre-push hook(.git/hooks/pre-push 或 git config core.hooksPath),可以自己加,但任何本地 hook 必须满足约束:
- hook 绝不允许 push、打 tag、发布、部署、修改凭据或重写工作树(不允许自动修复提交或静默修改文件)。它只能验证与报告;
- 为已知且书面记录的原因绕开自己的 hook(例如把进行中的工作推到自己的 fork 分支),用
git push --no-verify并在 PR 描述中说明。绕开本地 hook 不等于门禁通过——CI 仍然会跑,且被绕开的门禁绝不能被报告为已通过; - 发布(tag、GitHub Releases、crates/npm 工件)是独立的、需要 owner 批准的门禁。本地 hook 或本地绿色运行都不授权任何发布步骤。
提交信息:Conventional Commits 与 AI 协作署名
提交信息使用 conventional commits,文档给出了完整的前缀表:
| 前缀 | 用途 |
|---|---|
feat: |
新功能 |
fix: |
缺陷修复 |
docs: |
文档变更 |
refactor: |
代码重构 |
test: |
新增或更新测试 |
chore: |
维护任务 |
示例:feat: add doctor subcommand for system diagnostics。
文档对 AI 辅助提交持明确态度:AI 助手的 co-author trailer 是被允许的,使用助手是受欢迎的、无需披露,CI 也不再拒绝自动追加的 Co-authored-by: <some tool> 行。真正在意的是——做事的人类必须被署名,因为 Co-authored-by 会进入 GitHub 的贡献图谱。如果你想去掉自动追加的行,可以用交互式 rebase:
git rebase -i origin/main # 逐条 reword,删除 Co-authored-by 行
给人 co-author 是自由的,但地址必须是对方的 GitHub 关联地址(id+login@users.noreply.github.com),否则署名不被记录。这个细节的动机在后文的 Harvest 流程中还会再次出现。
最后一条约定与 Harvest 机制直接挂钩:当某个提交从社区 PR 收割代码时(见下文),提交正文中应包含 Harvested from PR #N by @author 行——一个自动关闭工作流会监视这个模式,并带着署名关闭被引用的 PR,让贡献者得到“自己的工作已发货”的明确信号。
你的贡献如何落地:Direct Merge 与 Harvest 两条路径
CodeWhale 遵循一个“land what's useful, credit the contributor(落地有用的,署名贡献者)”的模型,它有时会出乎新贡献者的预期。落地有两条路径。
路径 1 — 直接合并
如果你的 PR 范围清晰、通过 CI、不触碰信任边界面(auth / sandbox / publishing / branding)、且与 main 无冲突,维护者会直接合并。这是小型缺陷修复和测试完善的功能新增最常见的结果。
路径 2 — Harvest(收割)
如果 PR 体积大、混合了范围、与 main 冲突、或需要“维护者自己打磨比与贡献者来回沟通更快”的润色,维护者可能把有用的 commit 或 hunk 收割为 main 上的新 commit,而不是直接合并 PR。这不是拒绝——它意味着你的代码落地了。
发生这件事时的契约:
- 被收割 commit 的信息包含
Harvested from PR #N by @your-handle。这一行就是契约:它是你的署名,也是你的贡献已发货的信号; - 如果维护者复制或改写了你的代码,被收割 commit 在可能时保留原作者身份:要么在 cherry-pick 时保留 commit 作者,要么添加
Co-authored-by: Name <id+login@users.noreply.github.com>trailer。这是让 GitHub 的贡献界面识别“超出文字署名”的东西。文档同时告诫维护者:应使用.github/AUTHOR_MAP(该文件在本仓库中存在,见 .github/AUTHOR_MAP),或运行gh api users/<login> --jq '"\(.id)+\(.login)@users.noreply.github.com"',而不是从贡献者的机器上复制原始的、.local的或旧式 noreply 邮箱——docs/AGENT_ETHOS.md 中同样强调“不要把.local、占位符、bot/工具或原始第三方邮箱用于人类贡献者的署名”; - 下个 release 的
CHANGELOG.md条目以 handle 署名你; - 自动关闭工作流会用模板化的感谢与指向
main上 commit 的链接关闭你的 PR。
当维护者手工关闭一个被收割的 PR 时,关闭评论遵循固定模板(PR #2634 设定的模式):
Closing with harvest credit, @handle — <what landed> landed via
<commit sha(s) or PR #N>. <If work remains:> The remainder is tracked
in #NNN — follow-ups welcome there.
Thank you for <one specific thing the contribution got right>.
三个必需元素:贡献者的 handle、其工作落地的确切 commit 或 PR、以及(当 PR 包含比落地更多的内容时)剩余工作的跟踪 issue。被收割的 PR 永远不会被一个光秃秃的 “superseded” 关闭。
让下一次贡献走 Direct-Merge 路径
想让未来的贡献走更快的直接合并路径,杠杆最高的四件事:
- PR 保持单一目的。 每个 PR 一个缺陷修复;一个功能一个 PR。不要把重构和功能混在一起。
- 开 PR 前、CI 反馈后都 rebase 到当前
main。 冲突会把即使很小的变更也逼进 harvest 路径。 - 为新行为附测试。 维护者经常收割没有测试的 PR,因为自己加测试比向贡献者索要更快。
- 没有事先维护者签核,避开信任边界面。 这包括 auth/凭据流程、沙箱策略、发布/release 管道,以及
prompts/内容。未经事先讨论就触碰这些的 PR,即使实现良好,也不太可能被直接合并。
分层与 EPIC 规模的工作流
有些架构工作对单个 PR 来说太大,但仍需按依赖层级构建。针对这类变更的工作流:
- 当工作横跨多个 PR 时,从跟踪 issue 或 EPIC 开始。命名计划中的切片,并说明每个切片暂时不打算关闭什么。
- 每个实现 PR 只聚焦一个行为边界。
- 下层仍在移动时,后续层可以留在你的 fork 或开成 draft PR。栈式 PR 的标题或描述应写明
Draft / depends on #NNNN。 - 下层落地、分支 rebase 到当前
main、且 PR 以main为目标之前,依赖型 PR 不具备合并评审条件。 - PR 正文应说明:它建立在哪个更早的 PR 上、范围内有什么、明确排除什么、引用哪些 issue、运行了哪些本地命令。
- 仅当切片完全满足某个 issue 时才用
Closes #...;PR 推进了一个宽泛 issue 但留有后续工作时,用Refs #...并附简短的(partial)说明。 - 评审期间使用结构化 commit 没问题。维护者可能在合并时 squash 或 harvest,贡献者署名通过作者身份、co-author trailer、changelog 条目或 PR/issue 评论保留。当合并 commit 本身携带
Harvested from PR #N by @author行时,该 PR 会以 rebase 或 merge commit 而非 squash 合并,使该行完整到达main并触发自动关闭署名。
请求合并评审前,分层 PR 应满足:
- 已 rebase 到当前
main - 标记为 ready for review 而非 draft
- 聚焦一个行为边界
- PR 正文中有本地命令证据
- CI 绿色,或剩余红色通道有清晰解释
- 若变更了配置或 schema 行为,有往返(round-trip)或迁移保留测试覆盖
- 除非真正关闭,否则把宽泛 issue 标记为 partial
对分层工作,有用的 PR 描述形状:
Summary:
Scope:
Not in this slice:
Builds on:
Issues:
Validation:
Stewardship 分支
大型重构与架构工作在到达 main 之前先暂存于 codex/v0.9.0-stewardship 分支。该分支存在的意义:让多层系列(如命令组重构)可以针对稳定基础逐层落地、用其 parity harness 验证,然后通过周期性的 stewardship 合并流入 main——而不是让每一层去追 main 的日常变更。
对贡献者意味着:
- 分层/EPIC 规模的重构 PR 应以
codex/v0.9.0-stewardship为基础并指向该分支(可参考 #2888 的模型)。普通缺陷修复和功能仍指向main。 - 维护者周期性地把 stewardship 分支合并进
main;你的工作带着完整历史与署名到达main。 - 不确定用哪个基础时,在跟踪 issue 中询问——凡是多 PR 系列以外的一切,默认都是
main。
贡献门禁与 Agent 辅助改进
贡献门禁
CodeWhale 对社区前门使用维护者管理的贡献门禁;维护者与协作者自动绕过。门禁工作流默认 dry-run / 仅评论模式,让维护者先观察信号再改变贡献者流程。维护者姿态记录在 docs/AGENT_ETHOS.md:自动化应当降低负担,同时让善意贡献者被看见、被署名、能够继续帮忙。
Issue 永远不会被贡献门禁自动关闭。未批准的外部 issue 会收到一条要求补充复现细节的简短欢迎语,然后保持开放等待维护者分诊——CodeWhale 依赖真实用户的真实边缘情况,issue 入口应保持温暖开放。
PR 不同,因为它们可能触碰代码、CI、发布管道、auth、沙箱、provider 策略等信任边界面。PR 门禁可以在维护者认为需要这种安全控制时从 dry-run 切换为强制执行,但应把它当作评审负载控制,而非对贡献者质量的评判。在启用 PR 强制执行之前,应把 allowlist 播种得足够宽,覆盖不应被这次上线打扰的活跃外部贡献者。
Allowlist 的作用域:
pr:username允许 pull requestissue:username允许 issueall:username两者都允许
维护者可以在 PR 上评论 /lgtm 授予 PR 访问,或在 issue 上评论 /lgtmi 授予 issue 访问。裸命令 lgtm 和 lgtmi 出于兼容性也被接受,但带前缀的形态更受推荐——在普通评审讨论中更难被误触发。
批准不直接编辑 main:批准工作流会开一个小的 allowlist 更新 PR,使新条目在生效前可被评审。如果 PR 门禁误伤了优秀贡献者,走同样的批准流程恢复:评论 /lgtm、合并生成的 allowlist PR、再重新打开受影响的 PR;如果 GitHub 不允许重新打开已关闭的 PR,则在 allowlist PR 合并后请贡献者重新提交。
Agent 辅助改进
CodeWhale 允许自己帮助改进自己,但贡献仍必须被塑造成适合人类评审的形态。推荐的工作流来自私有 codewhale-ops 仓库中的递归自我改进提示:从全新的 fork 或分支运行它,让 agent 只找到一个小的摩擦点,一个补丁之后停止。DeepSeek V4 Pro 是当前这个循环的参考路径,但任何已配置的 provider 都可以——评审形态比 provider 更重要。
agent 与维护者都应遵循 docs/AGENT_ETHOS.md 中的 stewardship 姿态:用自动化产出证据、验证和窄补丁,最终社区决策保留给人类评审。有用的产出不是“改进想法”,而是:具体的复现、最小的 diff、聚焦的检查、以及解释权衡的 PR 描述。未经事先维护者签核,不要用 agent 触碰 auth、凭据、沙箱策略、发布/release 管道、provider 策略、遥测、赞助、品牌或全局 prompt。
工作区结构:你的改动落在哪里
CodeWhale 是一个 Cargo workspace。文档说明当前的运行主体与大部分 TUI、引擎、工具代码位于 crates/tui/src/,较小的工作区 crate 提供正在被逐步抽取出来的共享抽象。文档给出的结构表:
crates/
├── tui/ codewhale-tui 二进制(交互式 TUI + 运行时 API)
├── cli/ codewhale 二进制(分发器门面)
├── app-server/ HTTP/SSE + JSON-RPC 传输
├── core/ Agent 循环 / 会话 / 轮次管理
├── protocol/ 请求/响应分帧
├── config/ 配置加载、profile、环境变量优先级
├── state/ SQLite 线程/会话持久化
├── tools/ 类型化工具规格与生命周期
├── mcp/ MCP 客户端 + stdio 服务器
├── hooks/ 生命周期 hooks(stdout/jsonl/webhook)
├── execpolicy/ 审批/沙箱策略引擎
├── agent/ 模型/provider 注册表
对照当前 Cargo.toml 的 workspace members 可以看到,工作区实际还包含 build-support、command-contract、lane、paths、release、secrets、telemetry、workflow、workflow-js 等 crate——scripts/dev-test.sh --list 的区域表与之一一对应,新增 crate 后脚本区域表就是判断“我的改动该跑哪条最窄测试命令”的可靠索引。文档进一步指向 docs/ARCHITECTURE.md 了解这些 crate 之间的活数据流,包括自底向上的构建顺序。
default-members = ["crates/cli"] 这一配置解释了为什么裸 cargo build 只构建 cli 侧、以及 cargo run --bin codewhale 跑起来的是分发器而不是 TUI。
典型的 PR 形态
结构良好的 PR 遵循一致的形态。文档列举了近期的范例:
- #386 —
/init命令:新的crates/tui/src/commands/groups/project/init.rs模块、项目类型检测、AGENTS.md 生成、commands/mod.rs中的命令注册、本地化字符串; - #389 — 内联 LSP 诊断:
crates/tui/src/lsp/中的 LSP 子系统、crates/tui/src/core/engine/lsp_hooks.rs的引擎钩子、配置开关、测试覆盖; - #387 — 自更新:新的
crates/cli/src/update.rs模块、CLI 子命令注册、HTTP 下载 + SHA256 校验 + 原子二进制替换; - #393 —
/share会话 URL:新的crates/tui/src/commands/groups/project/share.rs、HTML 渲染、gh gist create集成、命令注册; - #343/#346 — (v0.8.5)运行时线程/轮次时间线与持久任务管理器重构。
这些路径均可在当前仓库中直接查看:crates/tui/src/commands/groups/project/ 下确实存在 init.rs、share.rs,crates/tui/src/lsp/ 目录包含 client.rs、diagnostics.rs、registry.rs,crates/cli/src/update.rs 也在列。典型规模:每个 PR 触及 1–3 个新文件,修改 2–5 个既有文件做接线(注册表、dispatch 匹配、本地化),并新增或更新测试。变更被限制在单个功能或修复内——如果你发现相关的、需要额外做的工作,开一个单独的 issue,而不是扩大 PR 范围。提交前,运行“Push 前的验证门禁”一节的命令。
提交变更、Issue 与安全披露
提交变更的标准流程
- 从
main创建功能分支:git checkout -b feat/your-feature - 做出修改并提交
- 运行 push 前验证命令(见上文门禁一节,含更严格的 release clippy 形态)
- 推送分支并创建 Pull Request
- 在 PR 描述中清晰描述变更
PR 指南
- 开 PR 时使用 .github/PULL_REQUEST_TEMPLATE.md 模板——它包含评审者预期的 Summary、Testing 与 Checklist 部分
- PR 聚焦单一变更
- 需要时更新文档
- 为新功能添加测试
- 请求评审前确保 CI 通过
报告 Issue
报告 issue 时使用模板:
- .github/ISSUE_TEMPLATE/bug_report.md — 可复现的问题或回归
- .github/ISSUE_TEMPLATE/feature_request.md — 想法与改进
Issue 报告应包含:操作系统与版本、Rust 版本(rustc --version)、codewhale 版本(codewhale --version)、复现步骤、预期与实际行为、相关错误信息或日志。
安全
如果发现安全漏洞,不要开公开 issue。见 SECURITY.md:鉴于 codewhale 是拥有文件操作、shell 执行与网络访问权限的编码 agent,漏洞需通过 GitHub 私有 advisory 或带 [SECURITY] 主题前缀的邮件私下报告;且只有最新稳定版接收安全补丁,旧版本不回填。
行为准则与许可证
保持尊重与包容,欢迎所有背景和经验水平的贡献者,完整条款见 CODE_OF_CONDUCT.md。按照 LICENSE 的 MIT 许可,向 codewhale 提交贡献即表示同意你的贡献以 MIT 许可发布。
关于贡献的疑问,随时开一个 issue 讨论即可。
atomcodeClaude Code 的开源替代方案。连接任意大模型,编辑代码,运行命令,自动验证 — 全自动执行。用 Rust 构建,极致性能。 | An open-source alternative to Claude Code. Connect any LLM, edit code, run commands, and verify changes — autonomously. Built in Rust for speed. Get StartedRust0623
Hy4-previewHy4 preview 是由腾讯混元团队研发的新一代混合专家(MoE)旗舰模型。模型总参数量 770B,每个 token 激活 49B,主干共包含78层,第一层采用标准 FFN,其余 77 层均为 MoE 结构,每层包含 256 个路由专家与 1 个共享专家,每个 token 激活 top-8 路由专家及共享专家。主干之外原生内置 1 层 MTP(总参数量 10B,激活 0.7B)以支持投机解码。Python00
GLM-5.3GLM-5.3 与 GLM-5.2 使用相同的基座模型——所有提升均来自后训练。与 GLM-5.2 相比,它在复杂编程和长程任务上的表现显著提升。Jinja00
GLM-5.3-FlashGLM-5.3-Flash (320B-A18B),是GLM-5系列的首个原生多模态模型。320B总参数,能力超过GLM-5.2Jinja00
Spark-X2.5-4BSpark-X2.5-4B 旨在让强大的 AI 更实用、更高效、更易获得。在广泛日常任务中表现强劲,涵盖对话、写作、翻译、推理、编码、工具调用以及智能体工作流,并在同等规模的开源模型中取得领先成绩。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00
Spark-X2.5-1.7BSpark-X2.5-1.7B 旨在让强大的 AI 更加实用、高效且易于获取。这些模型在广泛的日常任务中表现出色,涵盖对话、写作、翻译、推理、编程、工具调用和智能体工作流,并在同等规模的开源模型中取得领先结果。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00