您现在的位置是:首页 > 文章 > Spring 事件发布 网站文章

Spring 事件发布

孙玉超 2020-10-14 15:12:37 0 评论 911 浏览 0 收藏 0


其实在学校的时候就接触过事件,比如学古老的 Swing 时,那些按钮的监听,文本框的监听等等。再比如后来学习网页的时候,按钮的监听,文本框,鼠标等监听。这些监听和事件发布类似,它们需要三个关键要素。

事件源事件监听器。事件是框架中最容易被忽视的功能之一,但同时也是一个很有用的功能。像Spring其他特性一样,事件发布是 ApplicationContext 提供的功能之一。

事件通知是一个很有用的功能,使用事件机制可以将互相耦合的代码进行解耦,方便功能的新增或修改。


同步事件监听


首先定义一个类继承 ApplicationEvent 作为我们的事件类,然后在 Service 层写一个方法进行事件发布,也就是我们的事件源。Spring 使用 ApplicationEventPublisher 类来进行事件的发布 。 然后在当前 Service 或者其他 Service 再定义一个监听方法来监听我们的事件,代码如下:

//事件类
public class TestEvent extends ApplicationEvent {

    @Getter
    private final transient String str;

    public TestEvent(Object source , String str) {
        super(source);
        this.str = str;
    }
}

    //事件源(此方法写在业务层)
    public void test1(){
        applicationEventPublisher.publishEvent(new TestEvent(this,"sunyuchao"));
    }

   //事件监听(此方法写在业务层)
   @EventListener(TestEvent.class)
    public void testListen1(TestEvent testEvent){
        log.info(testEvent.getStr());
    }

上面代码就是最简单的一个同步事件发布,在我目前接触的案例,事件类主要是用来传递数据,然后在监听方法中去做我们的业务处理。


异步事件监听


Spring 事件还支持异步事件,只需要在监听器上加上 @Async 注解,SpringBoot 主启动类加上 @EnableAsync 注解就可以生效。

当使用异步事件监听时,需要注意以下限制:

  • 如果异步事件监听器抛出 Exception ,不会将其传播到调用方。可以查看 AsyncUncaughtExceptionHandler 来获取更多详细信息。

  • 异步事件监听方法无法通过返回值来发布后续事件。如果你确实需要发布后续事件,可以注入 ApplicationEventPublisher 来手动发布。


事务事件监听


这是应用最多的场景,一般我们 Service 层都是带事务的,当使用事务监听器时,首先事件源方法也就是发布事件的那个方法需要用 @Transactional 来修饰,其次监听器的注解不再使用@EventListener,而是@TransactionalEventListener。

@TransactionalEventListener 是对 @EventListener的 一个扩展,允许将事件的监听器绑定到事务的某个阶段。可以绑定到以下事务阶段:

  • AFTER_COMMIT (默认),事务提交后
  • AFTER_ROLLBACK ,事务回滚后
  • AFTER_COMPLETION ,事务完成,包括提交后和回滚后
  • BEFORE_COMMIT ,事务提交前

例如写监听器的时候可以这样写,@TransactionalEventListener(classes = TestEvent.class,phase = TransactionPhase.AFTER_COMMIT) 来控制在事务提交之后再执行监听事件。


注意自己测试的时候要引入数据库依赖,配置数据源。否则事务监听不会生效,博主当时就是因为这个莫名其妙,排查了好久,最后还是同事大佬给我定位到的问题……没有数据库的话,它默认 Service 层加 @Transactional 注解是不会生效事务的。另外如果使用 @TransactionalEventListener 注解,那么原来的 service 方法必须要加事务控制  @Transactional 注解,否则也不生效!





转载请注明出处:转载请注明出处

上一篇 : 迟来的Java8新特性 下一篇 : 阿里开源工具 EasyExcel

留言评论

所有回复

暮色妖娆丶

96年草根站长,2019年7月接触互联网踏入Java开发岗位,喜欢前后端技术。对技术有强烈的渴望,2019年11月正式上线自己的个人博客