核心是将策略选择与执行彻底分离,接口层仅暴露统一输入输出契约,通过策略工厂按参数动态路由,支持组合编排、上下文共享、表达式配置及降级兜底。

核心是把“策略怎么选”和“策略怎么执行”彻底分开,让接口调用方只关心传什么参数、要什么结果,不感知内部有多少种结算逻辑、它们如何组合或切换。
定义统一的结算行为契约
声明一个轻量接口,只暴露输入、输出和关键上下文字段,不暴露实现细节:
-
输入参数聚焦业务语义:比如
orderAmount、userId、couponCode、sceneType(如 “新客首单”、“大促会场”),而不是传一堆开关标志位 -
输出结构标准化:统一返回
SettlementResult,含finalAmount、appliedRules、breakdown等字段,下游无需解析不同实现的返回格式 -
避免在接口里塞策略选择逻辑:不写
if (sceneType.equals("vip")) return vipRule.apply(...)这类硬编码分支
用策略工厂 + 参数路由实现动态分发
把策略选择从接口方法中剥离,交给独立的工厂组件。调用方只需传参,工厂根据参数自动匹配并加载对应策略:
- 所有策略实现统一接口(如
SettlementStrategy),各自标注支持的@Supports(scene = "seckill", priority = 10) - 工厂启动时扫描所有策略 Bean,按
scene+priority建立映射表,支持运行时热更新(如从配置中心拉取最新规则权重) - 接口层调用时,仅需
strategyFactory.get(scene, userId).apply(request),完全解耦选择逻辑
支持组合与嵌套的参数化编排
复杂场景往往不是单一策略,而是多个子策略按条件/顺序叠加。这时参数本身成为流程控制器:
- 允许传入
compositionMode = "SEQUENTIAL"或"CONDITIONAL",驱动不同执行引擎 - 子策略间通过共享上下文(如
SettlementContext)传递中间结果,例如优惠券校验后写入context.setValidCoupon(...),后续满减策略直接读取,不重复查库 - 参数支持表达式,如
discountThreshold = "{{ orderAmount * 0.1 }}",让规则配置更灵活,避免每次改代码
对接口调用层做轻量适配与兜底
对外暴露的 Controller 或 OpenAPI 层应保持极简,只做参数校验、上下文组装和结果包装:
- 不做业务判断,不调用具体策略实现,只调用策略门面(Facade)或门面代理
- 统一异常处理:策略执行失败时,返回标准错误码(如
SETTLEMENT_STRATEGY_NOT_FOUND)+ 可读提示,不抛原始异常堆栈 - 内置降级策略:当所有匹配策略都不可用时,自动启用默认兜底策略(如仅应用基础折扣),保障接口可用性











