t2b.md 23 KB

T2B 协作清单

文档版本:v1.15 最后更新:2026-04-03 19:26:23

说明:

  • 本文件由总控维护,写给后端线程
  • 目标是把“后台生产闭环”第一阶段需要落地的东西讲清楚
  • 只写当前阶段实施说明,不写长讨论稿
  • 正式架构文档以 后台生产闭环架构草案 为准

0. 当前阶段状态与下一步

backend 当前已完成:

  • 生产骨架对象落库与 /dev/workbench 最小联调台
  • MapRuntimeBinding -> EventRelease -> launch.runtime 主链接通
  • EventPresentation / ContentBundle / EventRelease 第一阶段接通
  • Event 默认 active 三元组固化:
    • currentPresentationId
    • currentContentBundleId
    • currentRuntimeBindingId
  • publish 默认继承当前 active 三元组
  • Bootstrap Demo一键补齐 Runtime 并发布 已可从空白状态跑完整测试链
  • 一键标准回归回归结果汇总 已接入标准联调入口
  • 前端调试日志当前 Launch 实际配置摘要 已接入 workbench
  • 三类标准 demo 入口已显式挂出:
    • evt_demo_001
    • evt_demo_score_o_001
    • evt_demo_variant_manual_001
  • workbench 日志已补齐:
    • 分步日志
    • 真实错误
    • stack
    • 最后一次 curl
    • 预期判定

当前主线不再是继续补对象,而是进入:

联调标准化阶段

本阶段 backend 的核心任务只有 3 件事:

  1. 固化“一键测试”链路,确保从空白环境可重复跑通
  2. 固化详细日志口径,失败时明确定位在哪一步
  3. 固化稳定测试数据,并逐步支持更接近生产的真实输入

当前认为“真实输入替换第二刀”已经完成,backend 当前已完成:

活动卡片列表最小产品化配合第一刀

优先顺序建议:

  1. 维持现有一键回归链稳定
  2. 为活动列表页补最小卡片摘要接口或字段
  3. 保持活动详情页与列表页使用同一套活动摘要口径

说明:

  • 真实 content manifest
  • 真实 presentation schema
  • 真实 活动文案样例

这三类输入已接入,当前不再作为本轮重点。

原则:

  • 仍走同一条一键回归链
  • 不重新设计联调流程
  • 只是把 demo 输入逐步换成更接近生产的真实输入

当前 backend 不建议切去做:

  • 新的玩家侧页面入口
  • 更多管理对象
  • 更复杂后台 UI

0.5 当前分工

backend 当前这一轮已完成:

  1. 活动卡片列表最小字段集对应的后端摘要
  2. 卡片摘要接口/返回字段收口
  3. 默认体验活动与普通活动的状态标记

当前进入:

活动卡片列表最小产品化第一刀联调回归与小范围修复配合阶段

要求:

  • 继续挂在现有标准 demo 与一键回归链上
  • 不新开流程
  • 不新开对象层级
  • 优先响应前端在列表页第一刀联调中暴露的字段、默认值和语义问题

当前进一步明确 backend 的执行口径如下:

0.1 一键测试链路

请继续以这条链作为唯一标准联调入口维护:

Bootstrap Demo
-> 一键补齐 Runtime 并发布
-> launch / play / result / history 回归

要求:

  • 从空白环境直接可跑
  • 不依赖手工预铺 6~8 个对象
  • 同一条链可反复执行
  • 失败时能明确知道卡在哪一跳

0.2 详细日志口径

workbench 和相关 backend 调试输出,当前应至少统一包含:

  • 当前步骤名
  • 核心输入参数
  • 真实错误信息
  • stack
  • 最后一次 curl
  • 预期判定

不要只输出“失败了”,要能回答:

  • 是哪一步失败
  • 为什么失败
  • 用什么请求复现

0.3 稳定测试数据

当前 demo 数据不要继续散落手工维护,统一以 backend 准备的一键测试数据为准。

后续逐步支持以下更接近生产的真实输入:

  • 地图资源 URL
  • KML / 赛道文件
  • 内容 manifest
  • presentation schema
  • 活动文案样例

0.4 当前不建议做

联调标准化阶段不要继续发散去做:

  • 新对象扩张
  • 新管理面板
  • 更复杂 workbench UI
  • 复杂后台运营功能
  • 与当前联调闭环无关的页面能力

当前不建议 backend 继续发散去做:

  • 更多新对象
  • 更多 workbench 管理按钮
  • 更复杂后台 UI
  • 过早扩大奖励、社交、审核流

1. 本次目标

本次不是让 backend 一次性做完整后台,而是先搭出最小生产骨架,让下面这条链能真正闭环:

地图输入
-> 瓦片版本
-> KML 导入
-> 赛道 variant
-> 活动绑定
-> release
-> launch
-> 客户端消费

当前重点是:

  • 先把对象模型定下来
  • 先让地图、KML、活动三条输入链有正式落点
  • 先让客户端只认发布产物

补充确认:

  • 本次接受 backend 采用增量演进方式推进
  • 不要求一次性推翻当前已稳定联调的:
    • Event
    • EventRelease
    • Session 主链

当前补充确认:

  • 生产骨架第一阶段与活动运营域第二阶段第四刀已经完成
  • backend 当前下一步应切到“联调标准化”,而不是继续新增对象层级

2. 本次范围

2.1 本次必须做

  • 定义并落库以下核心对象:

    • Place
    • MapAsset
    • TileRelease
    • CourseSet
    • CourseVariant
    • CourseSource
    • Event
    • EventPresentation
    • ContentBundle
    • MapRuntimeBinding
    • EventRelease
  • 先让 KML 不再只是文件,而能转成 CourseVariant

  • 先让活动不再只是页面概念,而能正式绑定:

    • 展示定义
    • 内容包
    • 运行绑定
    • 发布版本
  • 第一阶段优先落以下对象:

    • Place
    • MapAsset
    • TileRelease
    • CourseSource
    • CourseSet
    • CourseVariant
    • MapRuntimeBinding
  • 第一阶段允许暂缓完整落库:

    • EventPresentation
    • ContentBundle 但对象语义必须先在架构上定清楚

2.2 本次先不做

  • 奖励系统
  • 社交系统
  • 复杂审核流
  • 完整后台 UI
  • 大而全的素材编排器
  • 高级权限体系

3. 后端对象最小理解

3.1 地图运行域

Place

  • 地点
  • 上层业务对象
  • 一个地点下可有多张地图

MapAsset

  • 某个地点下的一张地图资源
  • 一张地图可有多个瓦片版本

TileRelease

  • 某张地图的具体瓦片发布版本

CourseSet

  • 一组赛道集合
  • 例如:校园顺序赛、校园积分赛

CourseVariant

  • 一个具体可运行赛道方案
  • 顺序赛 8 点 / 12 点
  • 积分赛 A / B / C 方案
  • 客户端最终只应认这个对象

CourseSource

  • 原始输入源
  • KML 只是来源,不是最终业务对象

3.2 活动运营域

Event

  • 活动业务对象
  • 默认体验活动和定制活动都属于它

EventPresentation

  • 活动卡片、详情页、H5 schema

ContentBundle

  • 图片、音频、动画、文创、结果页资源等内容包

MapRuntimeBinding

  • 活动运行时绑定哪张地图、哪条赛道、哪套瓦片、哪套配置

EventRelease

  • 客户端真正消费的活动发布版本

4. 最小关系建议

建议 backend 先按这个关系理解:

  • Place 1 -> N MapAsset
  • MapAsset 1 -> N TileRelease
  • MapAsset 1 -> N CourseSet
  • CourseSet 1 -> N CourseVariant
  • CourseVariant N -> 1 CourseSource

  • Event 1 -> N EventPresentation

  • Event 1 -> N ContentBundle

  • Event 1 -> N MapRuntimeBinding

  • Event 1 -> N EventRelease

其中:

  • MapRuntimeBinding 负责引用:
    • placeId
    • mapId
    • tileReleaseId
    • courseSetId
    • courseVariantId

5. 后端第一阶段建议实施顺序

第一步:按增量方式落库最小对象

建议先把表和基础模型定下来。

第一阶段优先级建议:

  1. places
  2. map_assets
  3. tile_releases
  4. course_sources
  5. course_sets
  6. course_variants
  7. map_runtime_bindings

第二阶段再补:

  1. event_presentations
  2. content_bundles

说明:

  • 当前稳定的 events / event_releases / sessions 主链保留
  • 本次是在现有骨架上增量补生产对象,不做一次性替换式重构

第二步:先打通 KML 导入链

目标:

  • 上传 KML
  • 保存 CourseSource
  • 解析控制点与起终点
  • 生成一个 CourseVariant
  • 归入某个 CourseSet

第三步:先打通活动绑定链

目标:

  • 一个 Event 可绑定:
    • EventPresentation
    • ContentBundle
    • MapRuntimeBinding

第四步:先打通发布链

目标:

  • 生成 EventRelease
  • launch 先继续返回当前稳定字段:
    • resolvedRelease
    • business
    • variant
  • 第二阶段再补完整运行对象字段:
    • placeId
    • mapId
    • tileReleaseId
    • courseVariantId
    • eventReleaseId

第五步:把第一阶段生产骨架接口接入 /dev/workbench

目标:

  • 不让第一阶段对象只停留在 API 目录里
  • 在 workbench 里形成最小可操作联调面板
  • 用于验证对象关系和生产闭环,不用于替代正式后台

本步建议只做:

A. 地点与地图

  • Place 列表
  • 新建 Place
  • Place 下新建 MapAsset
  • MapAsset 下新建 TileRelease
  • 查看详情

B. 赛道与 KML

  • CourseSource 列表
  • 新建 CourseSource
  • 新建 CourseSet
  • CourseSet 下新建 CourseVariant
  • 查看详情

C. 运行绑定

  • MapRuntimeBinding 列表
  • 新建 MapRuntimeBinding
  • 选择:
    • place
    • map
    • tile release
    • course variant
  • 查看详情

本步明确不做:

  • 完整后台 UI
  • Event 全量编辑
  • EventPresentation 可视化搭建
  • ContentBundle 大资源管理台
  • Build / Release 全流程可视化
  • 删除、批量操作、审核流

一句话:

workbench 当前只做“第一阶段生产骨架联调台”,不做“正式后台管理系统”。

第六步:进入“最小接线”阶段

目标:

  • MapRuntimeBinding 和当前 EventRelease 接起来
  • 让运行对象开始逐步进入 launch
  • 保持当前前端稳定链不被打断

本步建议优先做:

A. EventReleaseMapRuntimeBinding

  • EventRelease 上补 runtimeBindingId
  • 查询 EventRelease 时可带出最小 runtime binding 摘要

B. launch 新增 runtime 摘要块

  • 保留当前稳定字段:
    • resolvedRelease
    • business
    • variant
  • 新增一个兼容性的 runtime 块,建议最少返回:
    • runtimeBindingId
    • placeId
    • mapId
    • tileReleaseId
    • courseSetId
    • courseVariantId
  • 如字段成本不高,可附带:
    • placeName
    • mapName
    • routeCode

C. workbench 最小接线验证

  • /dev/workbench 上增加:
    • EventRelease 选择或查看
    • 绑定 runtimeBinding
    • 查看 release 当前已接入的运行对象摘要

本步明确要求:

  • 不修改旧字段语义
  • 不移除旧字段
  • 不让前端现有 launch 链断掉
  • 先做到“后端可挂接、可透出、可验证”

6. 当前接口落地方向

当前阶段建议 backend 后续接口逐步收敛到:

6.1 生产侧接口

  • 创建地点
  • 创建地图
  • 创建瓦片版本记录
  • 上传 KML
  • 生成赛道 variant
  • 创建活动
  • 保存活动展示定义
  • 保存内容包引用
  • 保存运行绑定
  • 创建活动 release

6.2 客户端消费接口

  • 活动列表
  • 活动详情
  • launch
  • session start
  • session finish
  • result
  • history

关键要求:

  • 客户端只消费 release 产物
  • 不再消费原始 KML
  • 不再消费地图原始资产
  • launch 采用两阶段兼容,不要求第一阶段打断当前前端稳定链

6.3 workbench 联调台

backend 下一步建议把以下接口先接到 /dev/workbench

  • Place
  • MapAsset
  • TileRelease
  • CourseSource
  • CourseSet
  • CourseVariant
  • MapRuntimeBinding

接入目标:

  • list
  • create
  • detail
  • binding

不建议当前阶段接入:

  • edit
  • delete
  • batch
  • 审核流

6.4 最小接线阶段接口方向

backend 下一步建议新增或补齐以下能力:

  • EventRelease 挂接 runtimeBindingId
  • 查询 EventRelease 时返回最小运行绑定摘要
  • launch 返回新增 runtime 摘要块

当前目标不是让前端强依赖新字段,而是先让:

  • release 和 runtime binding 接上
  • launch 能把运行对象透出来
  • 前后端可以开始验证运行对象链是活的

6.5 第四刀:发布闭环阶段

在第三刀已经完成:

  • MapRuntimeBinding -> EventRelease
  • launch.runtime 兼容透出

之后,下一步建议进入真正的发布闭环阶段

目标:

  • 不再要求“先 publish,再手工 bind runtime”
  • 改为 publish 时就能直接产出带 runtimeBindingId 的完整 EventRelease
  • 保持当前旧接口和旧字段完全兼容

本步建议优先做:

A. publish/build 接口支持 runtimeBindingId

  • 在当前发布链中允许显式传入 runtimeBindingId
  • 如果传入,则发布完成后直接把 release 绑好 runtime
  • 如果不传入,则继续保持当前兼容行为

B. workbench publish 面板接入 runtime 选择

  • /dev/workbench 的发布操作区增加 Runtime Binding 选择
  • 支持一条完整联调链:
    • 选 release source / build
    • runtimeBindingId
    • publish
    • 直接 launch 验证

C. release 查询继续返回 runtime 摘要

  • Get Release
  • launch

都继续透出当前最小 runtime 摘要,供前端和总控验证。

本步关键要求:

  • 只加能力,不改旧语义
  • 新流程优先,但旧流程继续可用
  • 发布结果尽量原子,避免漏掉 runtime 挂接

7. 当前需要 backend 重点注意的边界

  1. KML 只是输入源,不是最终业务对象
  2. 活动不是素材仓库,活动只引用 ContentBundle
  3. 地图上层必须有 Place,不要让 MapAsset 直接当最上层
  4. 客户端最终必须只认 EventRelease
  5. launch 返回必须落到具体:
    • placeId
    • mapId
    • tileReleaseId
    • courseVariantId
    • eventReleaseId

8. 当前待 backend 回写确认

请 backend 线程后续重点回写以下确认:

  1. 第一阶段表结构是否接受这套对象拆分
  2. Place / MapAsset / TileRelease / CourseSource / CourseSet / CourseVariant / MapRuntimeBinding 是否按当前顺序推进
  3. KML 导入链是否准备按 CourseSource -> CourseVariant
  4. 活动是否接受拆成:
    • Event
    • EventPresentation
    • ContentBundle
    • MapRuntimeBinding
    • EventRelease
  5. launch 两阶段兼容方案是否按当前确认推进
  6. workbench 是否按“第一阶段生产骨架联调台”接入,且只做 list / create / detail / binding

本轮新增执行项:

  1. 是否按“第三刀最小接线”推进:

    • MapRuntimeBinding -> EventRelease
    • launch.runtime 摘要透出
    • 继续保持旧字段兼容
  2. 是否按“第四刀发布闭环”推进:

    • publish 直接支持 runtimeBindingId
    • workbench publish 面板增加 runtime 选择
    • 继续保留“先 publish,再 bind runtime”的兼容路径
  3. 是否进入“活动运营域第二阶段”:

    • EventPresentation 最小落库
    • ContentBundle 最小落库
    • EventRelease 明确绑定 presentation / bundle / runtime
  4. 是否进入“活动运营域第二阶段第二刀”:

    • event detail 透出最小 presentation / bundle 摘要
    • release detail 透出最小 presentation / bundle / runtime 摘要
    • launch 增加兼容性的 presentation / contentBundle 摘要块
    • publish 在未显式传入时允许按 event 当前默认配置自动补齐 presentation / bundle

9. 一句话结论

本次给 backend 的实施要求很简单:

先别继续围绕散装页面和散装配置推进,先把地图运行域和活动运营域的最小骨架搭起来。

当前下一步重点已经进一步明确为:

活动运营域第二阶段第三刀第一版已完成,backend 下一步切到“展示定义统一导入与默认绑定”阶段。

6.6 第五刀:前端正式接线阶段

当前 backend 已完成第四刀第一版:

  • publish 直接支持 runtimeBindingId
  • workbench publish 区支持直接填写 Runtime Binding ID
  • 发布成功返回 runtime
  • 旧的“先 publish,再 bind runtime”路径继续兼容

因此下一步建议正式进入前端接线阶段

目标:

  • 前端开始正式消费 launch.runtime
  • 活动准备页、地图页、结果页、历史页开始逐步展示运行对象摘要
  • 继续保持旧字段兼容,不要求一轮切掉老逻辑

前端第一阶段建议优先做:

A. launch.runtime 消费

  • 读取并缓存:
    • runtimeBindingId
    • placeId
    • mapId
    • tileReleaseId
    • courseSetId
    • courseVariantId
  • 如后端已返回名称摘要,也同步接入:
    • placeName
    • mapName
    • routeCode

B. 准备页与地图页最小展示

  • 在准备页展示当前地点 / 地图 / 赛道摘要
  • 在地图页调试或摘要区透出当前 runtime 对象

C. 结果与历史摘要逐步接入

  • 先不强改所有列表
  • 优先让单局结果页和历史详情页能看见:
    • place
    • map
    • variant
    • routeCode

当前阶段原则:

  • 前端正式上场,但只接新增摘要,不推翻现有稳定页面主链
  • resolvedRelease / business / variant 旧字段仍继续保留和可用
  • 如果后端某些名称摘要尚未补齐,前端先按 ID + 已有字段兜底

6.7 第六刀之后的下一步:活动运营域第二阶段第二刀

当前 backend 已完成:

  • 0009_event_ops_phase2.sql
  • EventPresentation 最小落库
  • ContentBundle 最小落库
  • EventRelease 已可绑定:
    • presentationId
    • bundleId
    • runtimeBindingId
  • publish 已支持显式挂接:
    • presentationId
    • contentBundleId
    • runtimeBindingId

因此下一步建议进入“活动运营域第二阶段第二刀”。目标是:

  • EventPresentation / ContentBundle 不只存在于后台和 publish 输入里
  • 而是正式进入可查询、可验证、可消费的发布摘要

建议顺序:

A. event detail 透出当前展示与内容包摘要

建议最少返回:

  • currentPresentation
    • presentationId
    • templateKey
    • version
  • currentContentBundle
    • bundleId
    • bundleType
    • version

B. Get Release 透出完整最小摘要

建议 release detail 同时包含:

  • presentation
  • contentBundle
  • runtime

前两者先以摘要形式返回,不先做复杂 schema 下发。

C. launch 增加兼容性的活动运营摘要块

在保持旧字段与当前 runtime 不变的前提下,新增:

  • presentation
  • contentBundle

建议最少包括:

  • presentationId
  • templateKey
  • bundleId
  • bundleType

D. publish 增加默认补齐逻辑

如果 publish 未显式传入:

  • presentationId
  • contentBundleId

允许按 event 当前默认配置自动补齐。

本步明确不建议做:

  • 前端立即全面消费 presentation / bundle
  • 复杂活动页面 schema 下发
  • 内容包全量资源编排
  • 正式后台大 UI

6.8 活动运营域第二阶段第三刀:发布摘要闭环与内容包导入入口

当前已确认:

  • frontend 已完成“活动运营域摘要第一刀”
  • 当前前端进入联调回归与小范围修复阶段
  • backend 下一步不应继续围绕前端页面做字段补丁,而应继续把活动运营域本身做完整

本刀建议拆成两步,但按一个阶段推进。

A. 先把 release 摘要闭环

目标:

  • EventRelease 真正成为活动运营域统一发布产物
  • 保证以下几处返回的摘要语义一致:
    • event detail
    • event play
    • launch
    • release detail

建议 release detail 最少透出:

  • presentation
    • presentationId
    • templateKey
    • version
  • contentBundle
    • bundleId
    • bundleType
    • version
  • runtime
    • runtimeBindingId
    • placeId
    • mapId
    • tileReleaseId
    • courseVariantId

同时建议 /dev/workbench 的 release 查看区,能直接验证这三类摘要。

B. 再打开 ContentBundle 统一导入入口

目标:

  • 不再只手工创建 ContentBundle
  • 让后续静态资源、音频、动画、文创等内容,先通过统一导入入口进入 bundle

当前阶段建议只做“入口”和“元信息”,不做完整资源平台。

建议最小能力:

  • 新增 ContentBundle Import 最小接口
  • 接收:
    • bundleType
    • sourceType
    • manifestUrl 或等价资源清单入口
    • version
    • title
  • 创建后生成:
    • bundleId
    • bundleType
    • version
    • assetManifest
    • status

当前明确不做:

  • 复杂资源上传工作流
  • 大文件管理台
  • 资源审核流
  • 全量 H5 schema 组装

关键原则:

  • ContentBundle 先做统一导入入口,不先做复杂资源管理系统
  • frontend 当前不消费资源明细,只继续认摘要
  • 先把“发布对象完整”和“内容资源有正式入口”两件事做起来

6.9 活动运营域第二阶段第四刀:展示定义统一导入与默认绑定

当前已确认:

  • backend 已完成:
    • event detail / play / launch / release detail 活动运营摘要闭环
    • ContentBundle 统一导入入口第一版
  • frontend 当前不再扩新页面链,继续联调回归

所以下一步 backend 不建议继续围绕玩家侧摘要补字段,而应继续把活动运营域生产链做完整。

A. 打开 EventPresentation 统一导入入口

目标:

  • 后续外部活动卡片/H5 搭建系统,不再只靠手工创建 presentation
  • 而是通过统一入口把展示定义正式导入 backend

建议最小能力:

  • 新增 EventPresentation Import 最小接口
  • 接收:
    • templateKey
    • sourceType
    • schemaUrl 或等价 schema 入口
    • version
    • title
  • 创建后生成:
    • presentationId
    • templateKey
    • version
    • schema
    • status

B. 固化 Event 当前默认 active 绑定

目标:

  • Event 当前默认使用的:
    • presentation
    • contentBundle
    • runtimeBinding 三者关系稳定下来

建议至少明确:

  • currentPresentationId
  • currentContentBundleId
  • currentRuntimeBindingId

以及 publish 在未显式传入时,默认如何继承这三者。

C. /dev/workbench 增加最小验证

建议补:

  • Import Presentation
  • 查看 event 当前 active:
    • presentation
    • bundle
    • runtime
  • 在 publish 区验证默认继承是否正确

当前明确不做:

  • 复杂展示编辑器
  • 全量 H5 schema 编排平台
  • 大型资源后台

关键原则:

  • EventPresentationContentBundle 都要有统一导入入口
  • Event 继续做业务壳和默认绑定,不吞大资源
  • 玩家前端继续只认发布摘要,不认后台草稿对象