Repository navigation
feat(git): add approval-gated advanced workflows - #120
Merged
Merged
Conversation
Qiyuanqiii
marked this pull request as ready for review
August 20, 2026 18:56
This was referenced Aug 20, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
摘要
git-advanced.v1:以封闭 operation union、capability、preview、typed failure、conflict、receipt 和兼容版本替代 raw Git argv;模型、HTTP、CLI 与 Desktop 均不能提供 Shell、可执行文件、环境、host path、任意 ref expression 或自定义 test command。stash@{n};tracked/index/untracked 分开投影,ignored 永不进入 stash;apply/pop 在 review 与 Git 调用前均复核 ignored file/directory collision,冲突时 pop 保留原 stash。git.advancedApproval、Workspace Checkpoint、operation-key、proposed -> runningCAS、common-dir 单一 running fence、append-only events 与 typed terminal receipt。cyberagent git-advanced、read/control bearer HTTP/OpenAPI、Desktop/React 高级 Git面板和 startup reconciliation;公共 DTO 隐藏 lease ID、managed host path、raw persistence JSON、argv、环境和进程身份。review升级到 1.4.0,focused-checks升级到 1.1.0;合并 Issue feat(code-intel): Go-owned LSP Runtime 与只读语义工具 #116 的 LSP 主线后,同时消费 source-bound LSP evidence 与完整 merge-base diff、stable hunk、base/ours/theirs、worktree/recovery evidence。Closes #117.
协议与操作矩阵
git-advanced.v1是 closed protocol,不是 Git command transport。每个 operation 只接受自己的字段,跨 operation 字段、重复 identity、非规范路径、非 exact OID、未知字段和超限输入在 review 前失败。hunk_stage/hunk_unstage/hunk_revertstash_create/stash_apply/stash_pop/stash_droprebase_start/continue/skip/abortcherry_pick_start/continue/skip/abortbisect_start/good/bad/skip/run/resetworktree_create/lock/unlock/remove/prune协议级固定上限包括 200 hunks、200 paths、128 commits、64 KiB spec JSON 和 1 MiB preview patch;SHA-1/SHA-256 object repository 均使用 exact lowercase object identity。
Preview、Approval、Checkpoint 与 exactly-once fence
每项 mutation 采用同一 durable flow:
git.advancedApproval;preview 本身不授权执行;proposed -> runningCAS 且赢得 exact common-dir 单一 running fence 的 caller 可以调用 Git;running记录只观察、不重放。无法证明命令是否已完成时记录interrupted/failed,绝不猜测成功。每次操作都建立 Checkpoint。preview 和 receipt 会明确披露不完整恢复:Workspace snapshot 能恢复有界文件与 raw index(包括 conflict stage 1/2/3),但不能保证复活已删除的 stash/ref、受管根中的外部 worktree 内容、进程、服务、网络或 Workspace 外文件。
Hunk 与 stash 的内容安全
before_sha256来自真实 source bytes,after_sha256来自仅应用所选 hunks 的内存结果;执行前再次投影并逐项比较。keep_index与restore_index为显式字段;include-ignored、任意 stash pathspec 和 selector 不可表达。status隐藏的 ignored content。Rebase、cherry-pick 与 bounded bisect
Rebase start 只允许 reviewed upstream 为 HEAD ancestor 的 clean attached local branch;存在 configured upstream 时按 shared history 处理并拒绝改写。Cherry-pick 只接受有序 exact single-parent commits。两者保存 original HEAD/branch、targets、current HEAD、sequencer SHA-256、conflict objects、generation 和 originating operation。
continue/skip/abort 只接受 durable sequence ID,并要求 live HEAD/sequencer 与 SQLite 行一致;外部执行
git rebase --continue或git cherry-pick --continue后不能用旧 preview 被静默接纳。冲突 receipt 投影 base/ours/theirs 与可用 recovery action。自动 bisect 只有两种固定 recipe:
go_test:go test -count=1 ./...;npm_test:仓库固定的 offline npm validation launcher。调用者只能选择 1–128 steps 与 1–900 秒 per-step timeout,不能提供 argv/Shell/executable/environment/network。每步绑定 exact commit、关闭 stdin、使用 stripped offline environment 和 whole-process-tree runner;缺少
tree_reaped、timeout、cancel 或 budget exhaustion 均产生 typed failure。这里的 offline 环境不是 OS 网络沙箱,repository test code 仍是显式审批后的 host execution。Managed worktree 生命周期
目标路径固定为
<managed-root>/<common-dir-fingerprint-prefix>/<safe-name>,调用者不提交 destination。registry 永久保存 path digest、repository/common-dir、branch、commit、Run、Workspace、generation 和 creating/last operation;name 即使 remove 后也不复用。managed root、common-dir 子目录、目标和父路径在 preview 与 mutation 前都检查 POSIX symlink 和 Windows junction/reparse traversal。remove 不带
--force,同时复核 registry/live HEAD、branch、common-dir、tracked、untracked、ignored 和 lock state;外部 commit drift 即使 worktree clean 也拒绝删除。prune 只处理 product registry 中已 missing 且 path hash 精确匹配的项。create 成功但 registry persistence 前崩溃时,reconciliation 只可登记 path/common-dir/branch/commit 全匹配、clean、unlocked、attached 的 exact target;原 operation 仍保持
failed/interrupted,不会伪造成功 receipt。Git 进程与安全边界
Git 使用替换环境并忽略 system/global config。实现显式关闭或拒绝:
固定 no-op ordinary editor 仅允许
rebase --continue使用 sequencer 已有 message,不启动用户编辑器。Windows case alias、.gitpath component、unsafe/quoted path、symlink/junction、submodule、detached HEAD、protected/shared branch、fork/upstream/base drift、literal pathspec metacharacter、cancellation、process-tree failure 与真实 conflict 都有回归覆盖。CLI、HTTP、Desktop 与文档
CLI:
preview/不带--confirm的run不创建 mutation;run --confirm才创建并批准 exact proposal 后执行。process capability 默认关闭,SQLite 中的旧记录不能在重启后重新启用它。HTTP/OpenAPI:
projection/discovery 使用 read bearer;review/execute 使用独立 control bearer。所有 body 为 128 KiB 内 closed JSON,unknown/duplicate field、GET body、重复 query、URL/body Run mismatch 和 stale generation 均拒绝。
Desktop 仅在 bootstrap capability 开启时显示“高级 Git”,并呈现 authority generation、repo/branch/upstream、hunk patch、stash role、base/ours/theirs conflict、sequence action、bisect progress、worktree state、Checkpoint limitation、Approval 与 immutable receipt;renderer 不接收 private lease ID 或 host path。
同步更新 README 中英文、usage、HTTP API、architecture、Desktop test matrix、Task/Status/Progress/Memory、独立
docs/git-advanced.md与 ADR 0122。主线兼容性与生成契约
最终 head
f9cedc5基于origin/main@715591a(PR #119 / Issue #116 LSP Runtime)。rebase 解决 13 个冲突,保留:code-intel-lsp.v1的 CLI/OpenAPI/Desktop/model-tool 路径与 runtime capability;focused-checks@1.1.0(SHA-256f5a6de08275e074efae00749bc2404a925fbc6a88ec25f37fcd1e9d8c69df28c);review@1.4.0(SHA-2569248f38a13048894382b0b79a9188ac1eb14d05f908f22b5f63a46a1c2feb07a);OpenAPI/TypeScript 连续生成字节一致:
116952142fb55bae2cfbe9b13f7e5742f16d14760989d0618acd0e6a43e240f8;2cb61016a393b5160bf6c37a2751f5d80bff5b5184aaddbd35290af860b284a4。验收条件对应
review/focused-checks可消费完整 merge-base diff、stable hunk、conflict、worktree、Checkpoint 与 recovery evidence,并保留 LSP source evidence。本地验证
最终重放主线后的完整发布门:
go test -p 2 -count=1 -timeout 30m ./...:全仓通过;Store748.018s、Application499.105s、HTTP133.862s、repository101.197s、CLI App98.970s。-race:repository83.453s、Application74.034s、Store18.235s、HTTP12.104s、CLI App11.568s、codeintel1.478s。-race:gitadvanced1.327s、workspacecheckpoint13.279s、Desktop35.400s。go test -tags "desktop,wv2runtime.error" -count=1 ./cmd/cyberagent-desktop ./internal/desktop ./internal/webui:0.772s / 20.282s / 0.425s。go vet、new-code scoped staticcheck、go mod verify、go mod tidy -diff、git diff --check通过。GOOS=linux GOARCH=amd64 CGO_ENABLED=0编译全部 58 个 Go test binary 通过。npm run check:api、strict TypeScript、完整 Web tests(65 files / 288 tests)、production build 通过;现有 Reactact/jsdom canvas/query warning 与 Monaco chunk warning 未升级为失败。npm audit --audit-level=high:0 vulnerabilities。fmt、locked tests(7 + 2)、Clippy 通过;重放前在线 RustSec audit 通过,最终cargo audit --no-fetch --no-yanked使用 1217 条缓存 advisory 扫描 41 个 locked dependency 通过;Cargo.lock 未变化。.env、SQLite/WAL、node_modules、Rust target、Desktop build 或其他本机运行时产物。已知主线/本机验证说明
无过滤
staticcheck -checks='SA*,S1*,QF*' ./...返回 8 项既有告警:internal/application/command_runtime.go:145SA4006;internal/codeintel/real_lsp_test.go:181S1016;internal/fileedit/fileedit.go:215SA9003;internal/plugins/package.go:281SA1019;internal/projectconfig/projectconfig.go:183SA4005;internal/sandbox/docker_container_io_export.go:291/294的SA1019/SA4011/S1023。以上 6 个文件相对
origin/main...HEAD均无 diff,本 PR 不把扩大扫描误写为 zero-warning;新增代码的 scoped scan 通过。第一次默认并发全仓运行在 main 原样的
TestCommandRuntimeForegroundCancellationReapsProcessTree遇到一次 Windows 负载敏感 cleanup deadline;隔离普通 20 次和 race 5 次均通过。随后完整 Application 复验在 main 原样、整个流程只有 500ms deadline 的TestUIEvidenceDeadlineReapsBuildJobBeforeApplicationLaunch中提前耗尽 source revalidation;隔离普通 20 次通过,race instrumentation 5 次中有 2 次复现 deadline 阶段漂移。最终项目惯用的-p 2全仓门完整通过,因此没有把两个未修改的主线测试或产品实现夹带进 #117。本机 Go 1.26.5 的
govulncheck ./...如实报告 5 项可达标准库 advisory:GO-2026-6218、GO-2026-6090、GO-2026-6089、GO-2026-5972、GO-2026-5026,均标记由 Go 1.26.6 修复。本 PR 未新增 Go module 依赖,不把该结果写成 zero finding。最终在线 RustSec refresh 曾遇到网络错误,因此当前 head 只声明使用最新本机 1217-advisory 缓存的 audit;不会把网络失败包装成在线通过。安全审计
.gitpath、symlink/junction、submodule 和 managed remove/prune deletion fence,并补充负向回归。非目标与残余边界
Audit
CI 状态
最终 head
f9cedc5的 GitHub Actions 全部通过:32396488102:Go control plane20m43s、TypeScript1m10s、Rust55s、真实 LSP(Ubuntu1m50s/ macOS1m12s/ Windows2m19s)、macOS Desktop2m52s、Windows Desktop9m32s、真实 Edge UI evidence1m53s,全部成功。32396488158:dependency/license boundary1m00s,可复现并验证的 Portable ZIP8m01s,全部成功;GitHub Release 发布在 pull request 事件上按设计 skipped。