跳转到内容

模型归属

参伍把职责分成三层。引擎负责必须确定、权威且可重放的部分;可选的扩展 crate 基于对外 API 提供通用领域机制,例如移动或法律;你的应用负责时代内容,以及赋予这些机制具体含义的各项决定。新增一条规则时,可以用这一页判断它该放在哪一层、代码应依赖哪个 crate。

依赖层次:应用和扩展 crate 构建在对外 API 之上,对外 API 封装引擎 crate. 查看图表源码.
查看图表源码
flowchart TB
  App["你的应用<br/>时代内容、场景、<br/>事故、权限记录"]
  Ext["扩展 crate<br/>canwu-movement、canwu-law、<br/>canwu-culture、canwu-society 等"]
  Ref["参考整合包<br/>canwu-reference-world 等<br/>可替换的示例"]
  Api["canwu-api<br/>对外 API"]
  Engine["引擎与机制 crate<br/>canwu-core、canwu-event、canwu-sim、<br/>canwu-routing、canwu-transport 等"]
  App --> Ext
  App --> Api
  Ext --> Api
  Ref --> Api
  Api --> Engine

箭头从一个 crate 指向它所依赖的 crate。引擎与机制 crate 从不依赖扩展、参考整合包或应用代码。

通用引擎 crate 拥有确定性的模拟契约:状态、结算、证据、随机性、持久化和重放。扩展 crate 和参考整合包拥有具体的世界概念,例如军队、政府、领土、人物和信件,以及描述这些概念的事件载荷。

需要跨多个插件修改记录时,同样遵循这条规则。例如,文化目标退休时,法律记录可能仍在引用它,这时的维护操作要同时修改不同插件拥有的记录。内核检查参与者集合、记录版本和工作预算,并保证所有修改要么一起提交,要么都不提交。每个参与者只能修改本插件拥有其 schema 的记录,目标记录的所有者插件还必须提交对该记录的精确修改。插件通过 register_owner_authorized_maintenance_participant 登记为参与者,或通过 register_maintenance_dependency_resolver 登记为依赖解析者。这两种登记都保存在插件描述符中,调用方无法漏掉某个参与者。

下表列出常见的关注点,说明哪个 crate 拥有相应机制,以及哪些事项由你的应用决定。

关注点 所有者 由你的应用决定
人物生存与人身状态、运行时创建人物、撤回排队输入 canwu-sim 核心状态与指令 人物何时死亡、被俘、获释或出现;撤回哪些输入
多所有者条件转移 canwu-sim 转移清单、第 10 阶段暂存与第 11 阶段审计 每次转移的参与者、预期版本和含义
规则评估证据 canwu-core 记录、canwu-sim 边界证据、canwu-api 视图读取 规则 ID 及各项的含义
决策谱系与席位继任 canwu-decision 票据与控制者绑定 谁占据席位、继任者何时接任
委托动用资源 canwu-resource 动用授权与 Granted 来源策略 谁可以授权给谁,以及权限证据记录
移动生命周期与运力池 canwu-movement 运行时记录与插件;canwu-transport 记录与纯函数分配 事故、危险、敌对行为及其随机抽样,以及权限依据记录
受托承运人与承运人扣押 canwu-correspondence 委托背后的关系,以及把扣押消息转告发送者
真伪判定 canwu-information 解读记录 伪造被识破的概率
加权、表决单元与征询程序阶段 canwu-law 编译后的程序 席位权重、表决单元和平局规则
引擎内文化结算 canwu-culture 的 CultureBoundaryPlugin 结算生命周期并产生变化;canwu-society 始终是 canwu.society:state 的唯一写入者 接触信号和文化定义
政策压力来源与 cohort 人口校准 canwu-society 人口校准所引用的外部存量记录
外部传播来源 canwu-technology 所引用的内容记录及其声明的可靠度

有两个移动相关的 crate 名字相近。canwu-reference-world 带有一个移动插件,用 order_movement_v1 命令移动示例世界中的军队和人物,属于可替换的示例代码;canwu-movement 则是面向 canwu-transport 记录的通用移动生命周期扩展,与参考世界无关。

canwu-event 只包含通用事件契约:

类型 说明
SimEvent 事件信封:身份、时间、受影响实体、摘要、原因和相关标识
EventKind 类型标签加扁平化的结构字段。领域 crate 定义强类型载荷,并用 from_payload 和 decode_payload 转换。
CauseRef 事件的原因:命令、父事件、边界或系统
EventAudience 哪些角色相对视图可以看到事件;插件未声明时为 Private
EventKindError 载荷无法编码或解码时返回的错误

移动、军队到达、人物旅行、信件交付、报告派发、知识和调试字段等强类型载荷,都放在拥有它们的整合包中。运行时保留了私有的兼容载荷,用来严格校验旧的事件标签和字段。插件事件带有插件名和事件类型,可以通过 EventKind::plugin_identity 取出。事件如何记录和呈现,见事件系统。

早期版本提供过一个 canwu-world crate,把一个示例世界放进了引擎的依赖图。它的十二个公开类型 MapPoint、Person、PersonTransitState、LetterStatus、LetterCargo、Government、Territory、Route、TransitState、Army、WorldSnapshot 和 WorldDiff,现在都在 canwu-reference-world 中。这个 crate 通过对外 API 提供它们,同时提供示例移动插件、脱离式投影和路由适配函数 planning_snapshot_from_world。canwu-routing 基于通用的 PlanningSnapshot 规划路线,不依赖示例世界。

canwu-sim 仍保留其中大部分类型的副本,并由 canwu-api 重新导出,供已弃用的 Canwu::world() 投影和旧式 Command::OrderMovement 路径使用。新代码应使用 canwu-reference-world 或自己的领域记录。逐个类型的归属理由见仓库中的世界与事件归属审计。