-- ============================================================================ -- pbl_runtime_ext / M11b:pbl_runtime_event 按月 RANGE 分区(mariadb 方言) -- 与 sql/pbl_runtime_ext.sql(由 tables.py 单一真源生成)配套使用: -- 新建环境:直接执行本文件的「A. 建表期分区」段 -- 已有环境(M11a 非分区表):执行「B. 一次性改造」段 -- 运行期:由模块 partitions.ensure_forward_partitions() 自动预建当月+未来 2 个月, -- 本文件仅提供等价 SQL 供 DBA 核对 / 应急手工执行(pmax 是最后兜底)。 -- 约束:RANGE 分区键必须进入主键与所有唯一键 → PK(id, created_at)、 -- uk_tenant_idem(tenant_id, idem_key, created_at)。 -- ============================================================================ -- ---------------------------------------------------------------- A. 建表期分区 -- 事件表 append-only:业务侧只 INSERT,本文件不提供任何 UPDATE/DELETE 语句。 CREATE TABLE IF NOT EXISTS `pbl_runtime_event` ( `id` BIGINT NOT NULL AUTO_INCREMENT COMMENT '主键', `tenant_id` BIGINT NOT NULL DEFAULT 0 COMMENT '租户ID(多租户强制打头)', `event_code` VARCHAR(64) NOT NULL COMMENT '事件编码', `idem_key` VARCHAR(128) NOT NULL DEFAULT '' COMMENT '幂等键(同键重复投递只落一条)', `world_id` BIGINT NOT NULL DEFAULT 0 COMMENT '世界ID(引用 world 基表,只读)', `session_id` BIGINT NOT NULL DEFAULT 0 COMMENT '游戏会话ID(引用 scense 基表,只读)', `entity_id` BIGINT NOT NULL DEFAULT 0 COMMENT '实体ID(引用 entity 基表,只读)', `event_type` VARCHAR(64) NOT NULL DEFAULT '' COMMENT '事件类型', `payload` TEXT COMMENT '事件负载 JSON', `seq_no` BIGINT NOT NULL DEFAULT 0 COMMENT '会话内单调序号(轮询游标)', `source` VARCHAR(32) NOT NULL DEFAULT 'runtime' COMMENT '来源:runtime/agent/script/client_intent', `state` VARCHAR(16) NOT NULL DEFAULT 'applied' COMMENT 'applied/rejected/rolled_back', `tx_group` VARCHAR(64) NOT NULL DEFAULT '' COMMENT '事务组(同组同事务)', `broadcast` TINYINT NOT NULL DEFAULT 1 COMMENT '是否参与广播 0/1', `state_version` BIGINT NOT NULL DEFAULT 0 COMMENT '本事件推进到的服务端权威版本', `created_by` BIGINT NOT NULL DEFAULT 0 COMMENT '创建人', `created_at` DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间(分区键)', PRIMARY KEY (`id`, `created_at`), UNIQUE KEY `uk_tenant_idem` (`tenant_id`, `idem_key`, `created_at`), KEY `ix_tenant_session_seq` (`tenant_id`, `session_id`, `seq_no`), KEY `ix_tenant_world` (`tenant_id`, `world_id`), KEY `ix_tenant_type` (`tenant_id`, `event_type`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='运行时事件流(append-only,按月 RANGE 分区,保留 14 个月)' PARTITION BY RANGE (TO_DAYS(`created_at`)) ( PARTITION `pbl_runtime_event_202609` VALUES LESS THAN (TO_DAYS('2026-10-01')), PARTITION `pbl_runtime_event_202610` VALUES LESS THAN (TO_DAYS('2026-11-01')), PARTITION `pbl_runtime_event_202611` VALUES LESS THAN (TO_DAYS('2026-12-01')), PARTITION `pbl_runtime_event_202612` VALUES LESS THAN (TO_DAYS('2027-01-01')), PARTITION `pbl_runtime_event_pmax` VALUES LESS THAN MAXVALUE ); -- ---------------------------------------------------------------- B. 一次性改造(M11a 非分区表 → 分区表) -- 顺序不可调换:先扩主键/唯一键,再 PARTITION BY。执行前请备份。 -- ALTER TABLE `pbl_runtime_event` DROP PRIMARY KEY, ADD PRIMARY KEY (`id`, `created_at`); -- ALTER TABLE `pbl_runtime_event` DROP INDEX `uk_tenant_idem`, -- ADD UNIQUE KEY `uk_tenant_idem` (`tenant_id`, `idem_key`, `created_at`); -- ALTER TABLE `pbl_runtime_event` PARTITION BY RANGE (TO_DAYS(`created_at`)) ( -- PARTITION `pbl_runtime_event_202609` VALUES LESS THAN (TO_DAYS('2026-10-01')), -- PARTITION `pbl_runtime_event_pmax` VALUES LESS THAN MAXVALUE -- ); -- ---------------------------------------------------------------- C. 月度维护(每月 1 日定时任务) -- 模块写入前会自动预建(ensure_forward_partitions,进程内 TTL 6h),下面是等价手工语句: -- ALTER TABLE `pbl_runtime_event` ADD PARTITION (PARTITION `pbl_runtime_event_202701` VALUES LESS THAN (TO_DAYS('2027-02-01'))); -- 查询当前分区: -- SELECT PARTITION_NAME, PARTITION_DESCRIPTION FROM information_schema.PARTITIONS -- WHERE TABLE_SCHEMA = DATABASE() AND TABLE_NAME = 'pbl_runtime_event'; -- 过期清理(保留 14 个月;DROP PARTITION 是元数据操作,不产生 DELETE 洪峰): -- 由 partitions.drop_expired_partitions(retain=14, dry_run=True) 先出清单, -- 人工确认后再 dry_run=False 执行,等价: -- ALTER TABLE `pbl_runtime_event` DROP PARTITION `pbl_runtime_event_202507`; -- ---------------------------------------------------------------- D. 实体状态 / 快照(M11a 定义不变) -- pbl_entity_state:服务端权威,state_version 由 apply_runtime_event 单调分配, -- 客户端提交值一律忽略;uk(tenant_id, session_id, entity_id, state_key) 支撑 UPSERT。 -- pbl_world_state_snapshot:掉线补齐/离线兜底基线,与事件同事务写入。 -- 见 sql/pbl_runtime_ext.sql(单一真源生成),本文件不重复定义,避免两处漂移。