抽象基类强制子类实现分表逻辑,编译器校验;定义gettargettablename等抽象方法,子类按业务规则返回物理表名;模板方法封装通用流程,确保分片行为一致。

在数据持久层用抽象方法强制规范各实体类的物理分表算法,核心是把“分到哪张表”这个决策权从通用框架收归业务实体自身,同时由编译器确保每个具体实体都明确回答这个问题——不实现?编译直接报错,不给上线机会。
定义抽象分表策略基类,留空关键分片逻辑
建一个抽象类(如 AbstractShardingEntity),声明一个抽象方法用于决定目标表名:
- protected abstract String getTargetTableName(String logicTableName, Object shardingKey);
- 该方法接收逻辑表名(如
t_order)和分片键值(如orderId),返回实际要操作的物理表名(如t_order_001) - 所在类必须用
abstract修饰,且不能被 new 实例化 - 禁止使用
private、static或final修饰该方法——它必须可被子类继承并重写
子类必须实现,否则无法编译通过
每个具体实体类(如 OrderEntity、UserEntity)继承该基类后,必须提供自己的分表逻辑:
- 例如
OrderEntity按订单 ID 取模:返回"t_order_" + (orderId % 16) - 例如
UserEntity按用户手机号哈希后取前两位:返回"t_user_" + hashPrefix - 若漏写或签名写错(比如参数类型用了
Long而非Object),编译器立刻报错:class OrderEntity must either be declared abstract or implement abstract method getTargetTableName(...) in AbstractShardingEntity
配合模板方法,统一执行流程但开放分片入口
在基类中封装通用的分表执行骨架,把分表计算作为唯一可变环节:
- 定义 public final List
resolveTableNames(String logicTableName, Collection - 内部调用
getTargetTableName()处理每个 key,并去重、排序、校验 - 子类无需关心怎么收集结果、怎么防重复、怎么处理空 key,只专注“这个 key 对应哪张表”
- 所有实体走同一套解析逻辑,避免各写一套导致行为不一致
支持精准与范围分片的双抽象契约
针对不同 SQL 场景,可声明两个抽象方法,分别约束不同语义的分片行为:
-
protected abstract String doPreciseSharding(String logicTableName, Object value); ——对应
=、IN等精准查询 -
protected abstract Set
doRangeSharding(String logicTableName, Range range); ——对应BETWEEN、>等范围查询 - 子类必须同时实现二者,才能成为具体类;任一缺失,编译失败
- 这样既覆盖常见分片场景,又让每种语义的实现责任清晰可追溯











