Spring---ApplicationContext的事件机制

版权声明:本文为博主原创文章,转载请注明作者和出处,如有错误,望不吝赐教。 https://blog.csdn.net/weixin_41888813/article/details/83624949

ApplicationContext的事件机制简介

1,事件源:ApplicationContext.publishEvent()方法:用于主动触发容器事件


2,事件:ApplicationEvent类,容器事件,必须由ApplicationContext发布(实际应用时,容器事件除了继承了ApplicationEvent类外,其实它就是一个普通的Java类


3,事件监听器:ApplicationListener接口,可由容器中任何监听器Bean担任。onApplicationEvent(ApplicationEvent event):用于对事件的处理每当容器内发生任何事件时,此方法都被触发。

这三者是什么关系?

ApplicationContext 通过publishEvent方法(该方法继承于接口ApplicationEventPublisher)发布事件(ApplicaitonEvent), 然后由ApplicationListener监听处理。 


实际上,Spring的事件机制与所有时间机制都基本相似,它们都需要事件源事件事件监听器组成。

只是此处的事件源是ApplicationContext,且事件必须由Java程序显式触发。下面的程序将演示Spring容器的事件机制。

事件机制一个例子

 1,先定义了一个ApplicationEvent类,其对象就是一个Spring容器事件,代码如下:

public class EmailEvent extends ApplicationEvent{
   private String address;
   private String text;
   public EmailEvent(Object source, String address, String text){
       super(source);
     this.address = address;
     this.text = text;
   }
   public EmailEvent(Object source) {
     super(source);
   }
   //......address和text的setter、getter
}

上面的EmailEvent类继承了ApplicationEvent类,除此之外,它就是一个普通的Java类。


2,容器监听器类代码如下:

public class EmailNotifier implements ApplicationListener {
    @Override
    public void onApplicationEvent(ApplicationEvent applicationEvent) {
        if (applicationEvent instanceof EmailEvent){
            EmailEvent emailEvent = (EmailEvent) applicationEvent;
            System.out.println("需要发送邮件的接收地址: " + emailEvent.getAddress());
            System.out.println("需要发送邮件的邮件正文: " + emailEvent.getText());
        }else {
            System.out.println("容器本身的事件: " + applicationEvent);
        }
    }
}

容器事件的监听器类必须实现 ApplicationListener 接口,并复写 onApplicationEvent() 方法

  • onApplicationEvent(ApplicationEvent event):每当容器内发生任何事件时,此方法都会被触发

3,将监听器配置在Spring的容器中,代码如下:

<bean class="org.spring.listener.EmailNotifier"/>

为Spring容器注册监听器,不需要像AWT编程那样采用代码进行注册,只需要在Spring的配置文件中进行简单配置即可。当我们在Spring中配置了一个实现了ApplicationListener的BeanSpring容器就会把这个Bean当成容器事件的监听器


4,主动触发容器事件,代码如下:

public class SpringTest {
    public static void main(String[] args){
        ApplicationContext ctx = new ClassPathXmlApplicationContext("spring-config.xml");
        //创建一个ApplicationEvent对象
        //EmailEvent ele = new EmailEvent("hello","[email protected]","this is a test");
        //主动触发该事件
        //ctx.publishEvent(ele);
    }
}

当系统创建Spring容器加载Spring容器时会自动触发容器事件容器事件监听器可以监听到这些事件。除此之外,程序也可以调用 ApplicationContext 的 publishEvent()方法主动触发一个容器事件


5,程序到此结束,运行结果如下:

容器本身的事件: org.springframework.context.event.ContextRefreshedEvent[source=org.springframework.context.support.ClassPathXmlApplicationContext@b81eda8: startup date [Thu Dec 04 20:20:52 CST 2014]; root of context hierarchy]


6,若取消main中的注释,即,使用publishEvent()来触发事件,运行结果如下:

容器本身的事件: org.springframework.context.event.ContextRefreshedEvent[source=org.springframework.context.support.ClassPathXmlApplicationContext@b81eda8: startup date [Thu Dec 04 20:24:03 CST 2014]; root of context hierarchy]

需要发送邮件的接收地址: [email protected]

需要发送邮件的邮件正文: this is a test

注意:如果Bean想发布事件,则Bean必须获得其容器的引用。如果程序中没有直接获取容器的引用,则应该让Bean实现ApplicationContextAware或者BeanFactoryAware接口,从而可以获得容器的引用。

详细介绍

ApplicationContext事件机制是观察者设计模式的实现,通过ApplicationEvent类ApplicationListener接口,可以实现ApplicationContext事件处理。

ApplicationListener Bean,每当ApplicationContext发布ApplicationEvent时,ApplicationListener Bean将自动被触发

Spring的事件框架有如下两个重要的成员:

  • ApplicationEvent:容器事件,必须由ApplicationContext发布
  • ApplicationListener:监听器,可由容器中的任何监听器Bean担任

扩展了解:Spring提供如下几个内置事件:

  • ContextRefreshedEvent:ApplicationContext容器初始化或刷新时触发该事件。此处的初始化是指:所有的Bean被成功装载,后处理Bean被检测并激活,所有Singleton Bean 被预实例化,ApplicationContext容器已就绪可用
  • ContextStartedEvent:当使用ConfigurableApplicationContext(ApplicationContext的子接口)接口的start()方法启动ApplicationContext容器时触发该事件。容器管理声明周期的Bean实例将获得一个指定的启动信号,这在经常需要停止后重新启动的场合比较常见(https://www.cnblogs.com/weilunhui/p/4143793.html
  • ContextClosedEvent:当使用ConfigurableApplicationContext接口的close()方法关闭ApplicationContext时触发该事件
  • ContextStoppedEvent:当使用ConfigurableApplicationContext接口的stop()方法使ApplicationContext容器停止时触发该事件。此处的停止,意味着容器管理生命周期的Bean实例将获得一个指定的停止信号,被停止的Spring容器可再次调用start()方法重新启动
  • RequestHandledEvent:Web相关事件,只能应用于使用DispatcherServlet的Web应用。在使用Spring作为前端的MVC控制器时,当Spring处理用户请求结束后,系统会自动触发该事件。

参考来源:

https://www.cnblogs.com/weilunhui/p/4143793.html

https://blog.csdn.net/maywehe/article/details/51660972

http://www.importnew.com/20890.html

猜你喜欢

转载自blog.csdn.net/weixin_41888813/article/details/83624949