Skip to content

[v2] 项目镜像与固定 snapshot 的同步 HTTP 接口 - #231

Merged
EricWvi merged 1 commit into
ora-space:mainfrom
ElephantGit:feat/774-project-repositories
Oct 30, 2026
Merged

EricWvi merged 1 commit into
ora-space:mainfrom
ElephantGit:feat/774-project-repositories

Conversation

@ElephantGit

Copy link
Copy Markdown
Contributor

项目需要先有可复用的固定仓库快照,执行侧才能按项目创建独立对话目录。新增 projectrepos 服务:校验当前成员和匿名 HTTPS 仓库/分支,完成一次 mirror clone、创建固定 snapshot ref,再写入已合并的 PostgreSQL 项目记录;失败不创建项目,之后不 fetch 或向上游写回。

新增同步候选接口 GET/POST /api/v2/tenants/{tid}/projects 和 GET /api/v2/tenants/{tid}/projects/{pid},支持分页与当前成员归属检查,创建者取真实登录身份,响应不暴露镜像路径或凭据。候选 OpenAPI 与真实 HTTP 测试一并交付,正式 v1 契约不变。内部 SeedDemo 可准备真实本地 Git 演示项目,不能由浏览器指定本地源。

本 PR 共 8 个交付文件,基于 main aae23e8;只新增 server.Options.Projects 和三条项目路由,不改 Execution/Catalog 注入。main 尚未装配项目服务,未配置时返回 503 projects_unavailable;正常启动 seed、Node、公共 Service 与最终入口另行交付。

验证:Go 1.27.1、PostgreSQL 17.11 下 gofmt、go vet ./...、TEST_DATABASE_URL=... go test -race -count=1 ./...、go build 和 git diff --check 全部通过。真实 Git/HTTP/PostgreSQL 用例覆盖缺失分支、clone 失败、固定 snapshot、隔离继承 Git 配置、归属验证先于远端访问、源仓库移除后的服务重建读取,以及并发/重复 demo seed;HTTP 响应按候选 OpenAPI 校验。

v2,不涉及 specs。

Refs ora-space/circus#774

@wanglongan587

Copy link
Copy Markdown
Collaborator

独立只读审查(成员,非本运行 reviewer)

审过 commit 7b39fbf285c013209e29244a12394be7841fb797。结论:未发现阻塞性正确性问题;有一处网络边界建议在合入前明确,其余是可以后置的小点。

已核对

  • Create 先 CheckExecutionScope,再校验入参,check-ref-format 在 clone 之前;clone 在 Root/.prepare-* 里完成,成功后 update-ref 固定 snapshot、删掉 remote.origin、rename 到 Root/<id>.git,最后才写库。失败路径不落项目;测试用请求计数证明越权创建不会触发远端访问。
  • Git 子进程环境整体替换(HOME=/dev/null、GIT_CONFIG_NOSYSTEM、GIT_CONFIG_GLOBAL=/dev/null、protocol.allow=never + protocol.https.allow=always、http.followRedirects=false、credential.helper=),--template= 不执行模板 hooks,输出限 4096 字节,错误不返回 stderr。测试实际用 GIT_CONFIG_GLOBAL / GIT_CONFIG_COUNT 污染父进程 env,验证不会被继承。
  • HTTP 侧拒绝未知字段、校验分页参数与成员归属;Project 响应不含镜像路径、snapshot ref;候选 OpenAPI 在测试里按真实响应逐条校验(含错误 shape)。
  • 与集成分支 c52500ed 比对,internal/projectrepos/**、internal/server/projects*.go 逐字一致(v2-server/README.md 因后续装配扩展而不同)。CI 在 head 上全绿(run 41033688737)。

需要明确的一点(非阻塞,但请给结论):HTTPS 目标没有 loopback / 私网限制

validURL 对 https 只校验 scheme 就返回 true,AllowLoopbackHTTP 只作用于 http。我在 head 上跑了临时探针:

https://127.0.0.1:8443/repo.git allowed=true
https://10.0.0.5/repo.git allowed=true
https://[::1]/repo.git allowed=true

也就是说,README 里「loopback 只在测试启用」只对 http 成立;生产中任何登录成员都能让后端去 clone 任意 HTTPS 主机(包括 loopback 和内网地址)。这是 v2-server 目前唯一由用户输入触发的服务端外连,属于 SSRF 面。两种收口都可以:明确写出信任模型(v2-server 只跑在本机/可信网络,成员可信),或者对 https 也拒绝 loopback/私网(解析后校验 IP,或用 host allowlist)。请 owner 或作者定一个并写进 README。

其余(都是小点,可以后置)

  • ErrRepositoryUnavailable 统一映射 400:上游不可达时更像 422/502,前端分不清「URL/分支填错」和「远端挂了」。候选契约自己定,确认即可。
  • 列表是 List 全量后在内存里过滤分页(internal/server/projects.go:88-104),项目多时每次请求 O(n);测试只覆盖 limit=0,建议补 after / nextCursor 的直接回归。
  • 没有租户级项目数或磁盘配额,clone 并发和体积只受两分钟超时约束。

@EricWvi
EricWvi merged commit fb1c393 into ora-space:main Oct 30, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants