Files
Genarrative/server-rs
suzmii ffd7510143
Project CI / AI game creator shell Rust lane 1/2 (pull_request) Has been cancelled
Project CI / AI game creator shell Rust lane 2/2 (pull_request) Has been cancelled
Project CI / AI game creator shell Rust crates (pull_request) Has been cancelled
Project CI / Backend tests (pull_request) Has been cancelled
Project CI / Native shell tests (pull_request) Has been cancelled
Project CI / Frontend tests (pull_request) Has been cancelled
Project CI / Repository checks (pull_request) Has been cancelled
Project CI / AI game creator shell web tests (pull_request) Has been cancelled
feat(游戏共创): 公开投影新增 coCreationCount(公开可见的全部后代数)
会议口径:共创页卡片要突出「共创次数(= 该作品有多少个子项目/衍生作品)」。前端已按 `coCreationCount`
接字段(TS 侧先声明 ⇒ 上轮 **dto parity 变红**:`GameDistributionGame 多出未登记字段/变体:coCreationCount`),
本提交把服务端补齐并让 parity 回绿。

- **字段**:公开投影新增 `coCreationCount`(Rust `co_creation_count: u64`)= **该作品子树里「公开可见的全部后代」
  数,不含自己**;沿血缘边 BFS 整棵子树,只数「未软删除 + 已公开」的后代(与 `forkCount` 同一批规则
  `module_game_distribution::counts_as_public_derivative`,只是深度不同)。已删/未公开的后代不进任何一层计数;
  **中间作品不可见也不断链**(它可见的后代仍计入祖先);血缘环/自引用按 visited 去重,自己永不计数。
- **与 `forkCount` 并存、互不推导**:`forkCount` = **直接**子代(「被改编 N」),`coCreationCount` = **全部**后代
  (「共创 N」);同卡上前者 ≤ 后者。
- **发出范围**:公开投影**恒发**(公开目录、公开详情、我的收藏、主题成员 `roots` 都走同一个 `public_game_payload`);
  **无后代时发 `0` 而不是缺键**;作者侧同形响应不发(与 `currentVersion`/`ratingSummary` 同类)⇒ 前端读取建议
  `coCreationCount ?? forkCount`。
- **算法与成本**:在 spacetime **只读事务内现算** —— 先建一次 `PublicDerivativeIndex`(父→直接子代边 + 可见性集合),
  再对本页每行做一次 BFS 子树计数(visited 去重);目录/详情/收藏/主题各自事务内建一次。
  **不新增表/列/索引、不落物化计数,api-server 只发键不遍历**;边际成本 O(作品数)(当前 51)。
- **契约/门禁**:parity 的 `public_game_payload` 构建器 `mustEmit` 把 `coCreationCount` 与 `forkCount` 一起钉住
  ⇒ **parity 由红转绿(EXIT 0)**;TS 契约里两字段注释改为最终口径。
- **文档**:主规范公开投影一行写明两字段口径、BFS 算法与成本。
- **测试**:+4(根带 3 直接子代、其中一个再带 1 孙代 ⇒ **`forkCount == 3`、`coCreationCount == 4`**;无后代两键恒发且为 0;
  不可见后代不计且**中间不可见不断链**;环/自引用安全)→ `module-game-distribution` **153 passed**。

门禁:`cargo check --all-targets` 0;`cargo test -p module-game-distribution` **153 passed**;
`cargo test -p api-server game_distribution` 见下文;**`check-game-distribution-dto-parity` 0(66 组 / 19 构建器 /
15 手拼类型)**;`check:spacetime-schema` 0(98 表);`cargo fmt --all -- --check` 0;`git diff --check` 0。
2026-10-07 18:02:13 +08:00
..
2026-07-17 16:56:46 +08:00
2026-09-20 18:33:02 +08:00
2026-07-17 16:56:46 +08:00

server-rs 工作区说明

更新时间:2026-05-15

server-rs/ 是当前唯一后端工作区,承载 Rust api-server、SpacetimeDB module、领域模块、平台副作用适配和共享契约。旧 server-node、Express、PostgreSQL、Go 服务端和 maincloud 口径均为历史残留,不再作为当前实现目标。

当前职责

  • crates/api-server:Axum HTTP / SSE / BFF 门面、鉴权、中间件、外部服务编排和 DTO 映射。
  • crates/spacetime-module:SpacetimeDB 表、reducer、procedure、事务 adapter、row mapper 和迁移。
  • crates/spacetime-client:后端访问 SpacetimeDB 的 typed facade。
  • crates/module-*:领域模型、命令、应用规则、领域事件和领域错误。
  • crates/platform-*:OSS、LLM、语音、认证等外部平台能力。
  • crates/shared-contracts:前后端共享 DTO 与公开契约。
  • crates/shared-kernel、crates/shared-logging、crates/tests-support:跨模块基础能力、日志和测试支撑。

开发规则

  1. server-rs/Cargo.toml 是 workspace 成员和依赖版本事实源;第三方依赖和 workspace 内 crate path 优先放在 [workspace.dependencies]。
  2. module-* 不直接依赖 Axum、SpacetimeDB table/reducer/procedure、reqwest、OSS、LLM、spacetime-client、tokio 或文件系统。
  3. api-server 不承接领域真相;发现领域规则时优先沉到对应 module-*。
  4. SpacetimeDB schema 变化必须同步 spacetime-module/src/migration.rs、生成绑定和当前后端架构文档的表目录。
  5. 人工命令、本地联调和文档示例不要使用 spacetime --root-dir。

常用命令

cargo check -p api-server --manifest-path server-rs/Cargo.toml
cargo test -p api-server --manifest-path server-rs/Cargo.toml
npm run check:server-rs-ddd
npm run check:spacetime-schema
npm run spacetime:generate
npm run dev:api-server

涉及 API smoke 时用 npm run dev:api-server 启动后端并检查 /healthz,不要使用旧 api-server:maincloud。

当前文档