15-ysyThread-观察者模式重构配置动态刷新
观察者模式重构配置动态刷新
如何在保持模块独立性的前提下,实现跨模块的高效通信?特别是在配置中心 Starter 需要通知 Web Starter 进行线程池参数更新时,传统的直接依赖方式会带来模块耦合、包体积膨胀等问题。为了解决这一挑战,引入了观察者模式
跨模块通信的设计挑战
1. 模块架构概览
1 | . |
和本文章相关的在 starter 模块下,子模块职责如下:
common-spring-boot-starter:提供配置解析、事件定义等公共能力nacos/apollo-spring-boot-starter:监听配置中心变更,触发刷新逻辑web-spring-boot-starter:管理Web容器线程池,响应配置变更
2. 理想的解决方案
我们需要一种机制,能够完成以下需求:
- 解耦模块依赖:配置中心 Starter 无需直接依赖具体的线程池管理模块
- 支持动态扩展:新增线程池适配器时,无需修改现有代码
- 保持高内聚:每个模块专注自己的核心职责
- 简化测试:模块间松耦合,便于单元测试和集成测试
为什么选择观察者模式?
1. 业务场景分析
配置变更的处理流程如下:
【配置中心变更】 →【 配置解析】 → 【参数对比】 → 【线程池更新】 → 【变更通知】
- 一个事件源:配置中心的配置变更
- 多个观察者:动态线程池管理器、
Web线程池管理器、RocketMQ线程池管理器、自定义线程池管理器等。甚至加点想象力,是不是连接池动态变更也能做
2. 观察者模式的优势
动态扩展能力
新增线程池适配器时,只需:
- 开发监听者,实现
ApplicationListener<ThreadPoolConfigUpdateEvent>接口 - 将监听者注册为
Spring Bean,无需修改任何现有代码
1 | // 第一步 |
什么是观察者模式?
1. 观察者模式定义
观察者模式 是一种行为设计模式,它定义了对象间的 一对多依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都会得到通知并自动更新
2. 核心角色
Subject(主题/被观察者):维护观察者列表,提供注册、移除观察者的方法Observer(观察者):定义更新接口,当收到主题通知时执行相应操作ConcreteSubject(具体主题):实现主题接口,状态改变时通知所有观察者ConcreteObserver(具体观察者):实现观察者接口,定义具体的更新逻辑
3. 经典实现示例
以新闻订阅为例
ysyThread 中的观察者模式实现
1. Spring 事件机制
基于 Spring 的事件发布机制实现观察者模式
2. 事件定义
1 | public class ThreadPoolConfigUpdateEvent extends ApplicationEvent { |
事件类设计要点:
- 继承
ApplicationEvent,符合Spring事件规范- 携带配置信息
BootstrapConfigProperties,为观察者提供必要数据
3. 事件发布者(被观察者)
1 | // 发布线程池配置变更事件(观察者模式的核心) |
4. 事件观察者实现
1 | // 1. 实现 ApplicationListener<ThreadPoolConfigUpdateEvent> 接口 |
扩展性分析
Guava vs Spring 观察者模式
| 维度 | **Spring ApplicationEvent **✔️ | Guava EventBus |
|---|---|---|
| 所属框架 | Spring 框架 |
Guava 工具库 |
| 事件订阅方式 | 实现 ApplicationListener 或 @EventListener 注解监听 |
使用 @Subscribe 注解的方法监听 |
| 注册监听器 | 自动注册(通过 Spring 容器扫描 Bean) |
需手动注册到 EventBus |
| 同步/异步支持 | 默认同步,支持 @Async 异步 |
默认同步,也支持 AsyncEventBus 异步 |
| 解耦程度 | 高,基于事件名称和类型,天然解耦 | 中,需显式注册对象 |
整体来看,Spring 事件机制与 Guava EventBus 在实现观察者模式上并无本质差异,都适用于常规的业务解耦场景。不过,考虑到 Spring 提供了原生支持,且生态完善、集成便捷,更推荐优先使用 Spring 的事件监听机制,无需额外引入 Guava 依赖
同时,如果在代码中直接 ApplicationContext 发布事件监听,还能通过 IDEA 自带图标看到对应的观察者集合,Guava EventBus 是没有这个展示的
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 涯思构码·易思涯!









