# 抓大鹅 Match3D B4+B5 spacetime-client 与 api-server facade 落地记录 日期:`2026-04-30` ## 1. 本阶段目标 本文件记录 B4+B5 的技术落地范围:把 B3 已生成的 Match3D SpacetimeDB procedure 接到 `spacetime-client`,再通过 `api-server` 暴露给前端使用的 HTTP facade。 本阶段不改 SpacetimeDB 表结构,不新增 migration,不接入真实题材素材生成,也不改前端即时反馈实现。 ## 2. 已落地范围 ### 2.1 SpacetimeDB bindings 使用仓库封装脚本重新生成 bindings: ```powershell npm run spacetime:generate ``` Windows 下 SpacetimeDB CLI 可能在 Rust bindings 已生成后输出 `Could not format generated files: 文件名或扩展名太长。 (os error 206)`。脚本已调整为:当 CLI 退出码为 `0` 且只是格式化警告时继续同步生成文件。 生成文件仍视为机器产物,禁止手写修改。 ### 2.2 spacetime-client facade 新增: ```text server-rs/crates/spacetime-client/src/match3d.rs ``` 并在 `spacetime-client/src/lib.rs` 导出 `match3d` 模块与 Match3D Record 类型。 已覆盖: 1. 创作会话:create / get / submit message / finalize / compile draft。 2. 作品:list / get detail / update / publish / delete / public gallery list。 3. 运行态:start / get / click / stop / restart / time-up。 `mapper.rs` 负责把 procedure 返回的 JSON 字符串解析为稳定 Record,不把 generated bindings 泄露到 `api-server`。 ### 2.3 api-server HTTP facade 新增: ```text server-rs/crates/api-server/src/match3d.rs ``` 并在 `main.rs` 注册模块,在 `app.rs` 挂载路由。 已挂载路由: ```text POST /api/creation/match3d/sessions GET /api/creation/match3d/sessions/{session_id} POST /api/creation/match3d/sessions/{session_id}/messages POST /api/creation/match3d/sessions/{session_id}/messages/stream POST /api/creation/match3d/sessions/{session_id}/actions POST /api/creation/match3d/sessions/{session_id}/compile GET /api/creation/match3d/works GET /api/creation/match3d/works/{profile_id} PATCH /api/creation/match3d/works/{profile_id} PUT /api/creation/match3d/works/{profile_id} DELETE /api/creation/match3d/works/{profile_id} POST /api/creation/match3d/works/{profile_id}/publish GET /api/runtime/match3d/gallery POST /api/runtime/match3d/works/{profile_id}/runs GET /api/runtime/match3d/runs/{run_id} POST /api/runtime/match3d/runs/{run_id}/click POST /api/runtime/match3d/runs/{run_id}/stop POST /api/runtime/match3d/runs/{run_id}/restart POST /api/runtime/match3d/runs/{run_id}/time-up ``` `api-server` 返回 `shared-contracts` 中的 Match3D DTO,前端不需要感知 SpacetimeDB 内部 JSON 快照结构。 ## 3. 创作 Agent 当前口径 B5 首版先采用确定性配置抽取,不在本阶段新增真实 LLM prompt: 1. 创建会话时可从 `themeText / seedText / clearCount / difficulty / referenceImageSrc` 形成配置。 2. 发送消息时根据用户文本或 `quickFillRequested` 更新题材、需要消除次数和难度。 3. `match3d_compile_draft` 动作调用 SpacetimeDB `compile_match3d_draft`,生成 draft work profile。 后续若要接真实 LLM turn,应复用现有创作 Agent 公共编排,并保持 submit/finalize 两阶段职责不变。 ## 4. 运行态确认协议 B5 保持 PRD 调整后的边界: 1. 前端负责点击、飞入、入槽、三消、腾格、胜负等即时表现。 2. 后端通过 `click_match3d_item`、`finish_match3d_time_up` 等 procedure 做权威确认。 3. HTTP response 会把 SpacetimeDB `Accepted / VersionConflict / RunFinished` 等状态归一到前端 shared contract 可消费的 `accepted / rejectReason / run` 结构。 4. `snapshotVersion` 继续作为前端即时反馈和后端确认之间的版本校验字段。 ## 5. shared contract 对齐 本阶段补齐 Rust shared contract 与 TypeScript contract 的已知差异: 1. `Match3DAgentSessionSnapshotResponse` 增加 `anchorPack`。 2. `Match3DResultDraftResponse` 增加 `profileId / summaryText / totalItemCount`,同时保留 `summary` 兼容结果页读取。 3. `PutMatch3DWorkRequest` 增加可选 `themeText`,结果页可编辑题材;旧请求缺省时 API 会沿用已有作品题材。 ## 6. 验收命令 本阶段至少执行: ```powershell cargo check -p spacetime-client --manifest-path server-rs\Cargo.toml cargo check -p api-server --manifest-path server-rs\Cargo.toml cargo test -p shared-contracts match3d --manifest-path server-rs\Cargo.toml npm run check:encoding npm run api-server:maincloud ``` `api-server:maincloud` 是修改后端后的必跑项;如果本地缺少 Maincloud 环境或 SpacetimeDB 发布态不一致,需要在最终结果里明确说明。 ## 7. 后续接入点 1. F1/F2/F3 可把 mock client 替换到上述 HTTP facade。 2. F4 平台分发可先读取 `/api/runtime/match3d/gallery` 的已发布作品列表。 3. 若后续要记录排行榜或作品播放统计,需要补 Match3D 成绩表或 play record procedure,并同步更新 migration。