跳至主要內容

Spring 事件

钝悟...大约 4 分钟Java框架SpringSpring核心Java框架Spring

Spring 事件

Java 事件/监听器编程模型

设计模式 - 观察者模式扩展

  • 可观者对象(消息发送者) - java.util.Observable
  • 观察者 - java.util.Observer

标准化接口

  • 事件对象 - java.util.EventObject
  • 事件监听器 - java.util.EventListener

面向接口的事件/监听器设计模式

事件/监听器场景举例

Java 技术规范事件接口监听器接口
JavaBeansjava.beans.PropertyChangeEventjava.beans.PropertyChangeListener
Java AWTjava.awt.event.MouseEventjava.awt.event.MouseListener
Java Swingjavax.swing.event.MenuEventjavax.swing.event.MenuListener
Java Preferencejava.util.prefs.PreferenceChangeEventjava.util.prefs.PreferenceChangeListener

面向注解的事件/监听器设计模式

事件/监听器注解场景举例

Java 技术规范事件注解监听器注解
Servlet 3.0+@javax.servlet.annotation.WebListener
JPA 1.0+@javax.persistence.PostPersist
Java Common@PostConstruct
EJB 3.0+@javax.ejb.PrePassivate
JSF 2.0+@javax.faces.event.ListenerFor

Spring 标准事件 - ApplicationEvent

Java 标准事件 java.util.EventObject 扩展

  • 扩展特性:事件发生事件戳
  • Spring 应用上下文 ApplicationEvent 扩展 - ApplicationContextEvent
  • Spring 应用上下文(ApplicationContext)作为事件源

具体实现:

  • org.springframework.context.event.ContextClosedEvent
  • org.springframework.context.event.ContextRefreshedEvent
  • org.springframework.context.event.ContextStartedEvent
  • org.springframework.context.event.ContextStoppedEvent

基于接口的 Spring 事件监听器

Java 标准事件监听器 java.util.EventListener 扩展

  • 扩展接口 - org.springframework.context.ApplicationListener
  • 设计特点:单一类型事件处理
  • 处理方法:onApplicationEvent(ApplicationEvent)
  • 事件类型:org.springframework.context.ApplicationEvent

基于注解的 Spring 事件监听器

Spring 注解 - @org.springframework.context.event.EventListener

特性说明
设计特点支持多 ApplicationEvent 类型,无需接口约束
注解目标方法
是否支持异步执行支持
是否支持泛型类型事件支持
是指支持顺序控制支持,配合 @Order 注解控制

注册 Spring ApplicationListener

  • 方法一:ApplicationListener 作为 Spring Bean 注册
  • 方法二:通过 ConfigurableApplicationContext API 注册

Spring 事件发布器

  • 方法一:通过 ApplicationEventPublisher 发布 Spring 事件
    • 获取 ApplicationEventPublisher
      • 依赖注入
  • 方法二:通过 ApplicationEventMulticaster 发布 Spring 事件
    • 获取 ApplicationEventMulticaster
      • 依赖注入
      • 依赖查找

Spring 层次性上下文事件传播

  • 发生说明
  • 当 Spring 应用出现多层次 Spring 应用上下文(ApplicationContext)时,如 Spring WebMVC、Spring Boot 或 Spring Cloud 场景下,由子 ApplicationContext 发起 Spring 事件可能会传递到其 Parent ApplicationContext(直到 Root)的过程
  • 如何避免
  • 定位 Spring 事件源(ApplicationContext)进行过滤处理

Spring 内建事件

ApplicationContextEvent 派生事件

  • ContextRefreshedEvent :Spring 应用上下文就绪事件
  • ContextStartedEvent :Spring 应用上下文启动事件
  • ContextStoppedEvent :Spring 应用上下文停止事件
  • ContextClosedEvent :Spring 应用上下文关闭事件

Spring 4.2 Payload 事件

Spring Payload 事件 - org.springframework.context.PayloadApplicationEvent

  • 使用场景:简化 Spring 事件发送,关注事件源主体
  • 发送方法:ApplicationEventPublisher#publishEvent(java.lang.Object)

自定义 Spring 事件

  • 扩展 org.springframework.context.ApplicationEvent
  • 实现 org.springframework.context.ApplicationListener
  • 注册 org.springframework.context.ApplicationListener

依赖注入 ApplicationEventPublisher

  • 通过 ApplicationEventPublisherAware 回调接口
  • 通过 @Autowired ApplicationEventPublisher

依赖查找 ApplicationEventMulticaster

查找条件

  • Bean 名称:"applicationEventMulticaster"
  • Bean 类型:org.springframework.context.event.ApplicationEventMulticaster

ApplicationEventPublisher 底层实现

  • 接口:org.springframework.context.event.ApplicationEventMulticaster
  • 抽象类:org.springframework.context.event.AbstractApplicationEventMulticaster
  • 实现类:org.springframework.context.event.SimpleApplicationEventMulticaster

同步和异步 Spring 事件广播

基于实现类 - org.springframework.context.event.SimpleApplicationEventMulticaster

  • 模式切换:setTaskExecutor(java.util.concurrent.Executor) 方法
    • 默认模式:同步
    • 异步模式:如 java.util.concurrent.ThreadPoolExecutor
  • 设计缺陷:非基于接口契约编程

基于注解 - @org.springframework.context.event.EventListener

  • 模式切换
    • 默认模式:同步
    • 异步模式:标注 @org.springframework.scheduling.annotation.Async
  • 实现限制:无法直接实现同步/异步动态切换

Spring 4.1 事件异常处理

Spring 3.0 错误处理接口 - org.springframework.util.ErrorHandler

使用场景

  • Spring 事件(Events)
    • SimpleApplicationEventMulticaster Spring 4.1 开始支持
  • Spring 本地调度(Scheduling)
    • org.springframework.scheduling.concurrent.ConcurrentTaskScheduler
    • org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler

Spring 事件/监听器实现原理

核心类 - org.springframework.context.event.SimpleApplicationEventMulticaster

  • 设计模式:观察者模式扩展
    • 被观察者 - org.springframework.context.ApplicationListener
      • API 添加
      • 依赖查找
    • 通知对象 - org.springframework.context.ApplicationEvent
  • 执行模式:同步/异步
  • 异常处理:org.springframework.util.ErrorHandler
  • 泛型处理:org.springframework.core.ResolvableType

问题

Spring Boot 事件

事件类型发生时机
ApplicationStartingEvent当 Spring Boot 应用已启动时
ApplicationStartedEvent当 Spring Boot 应用已启动时
ApplicationEnvironmentPreparedEvent当 Spring Boot Environment 实例已准备时
ApplicationPreparedEvent当 Spring Boot 应用预备时
ApplicationReadyEvent当 Spring Boot 应用完全可用时
ApplicationFailedEvent当 Spring Boot 应用启动失败时

Spring Cloud 事件

事件类型发生时机
EnvironmentChangeEvent当 Environment 示例配置属性发生变化时
HeartbeatEvent当 DiscoveryClient 客户端发送心跳时
InstancePreRegisteredEvent当服务实例注册前
InstanceRegisteredEvent当服务实例注册后
RefreshEvent当 RefreshEndpoint 被调用时
RefreshScopeRefreshedEvent当 Refresh Scope Bean 刷新后

Spring 事件核心接口/组件

  • Spring 事件 - org.springframework.context.ApplicationEvent
  • Spring 事件监听器 - org.springframework.context.ApplicationListener
  • Spring 事件发布器 - org.springframework.context.ApplicationEventPublisher
  • Spring 事件广播器 - org.springframework.context.event.ApplicationEventMulticaster

Spring 同步和异步事件处理的使用场景

  • Spring 同步事件 - 绝大多数 Spring 使用场景,如 ContextRefreshedEvent
  • Spring 异步事件 - 主要 @EventListener 与 @Async 配合,实现异步处理,不阻塞主线程,比如长时间的数据计算任务等。不要轻易调整 SimpleApplicationEventMulticaster 中关联的 taskExecutor 对象,除非使用者非常了解 Spring 事件机制,否则容易出现异常行为。

参考资料

评论
  • 按正序
  • 按倒序
  • 按热度
Powered by Waline v2.15.7