广告
返回顶部
首页 > 资讯 > 精选 >Spring事件发布与监听怎么实现
  • 700
分享到

Spring事件发布与监听怎么实现

2023-06-02 13:06:26 700人浏览 安东尼
摘要

这篇文章主要讲解了“spring事件发布与监听怎么实现”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Spring事件发布与监听怎么实现”吧!  一、事件监听相关概念介绍  1、流程分析  事

这篇文章主要讲解了“spring事件发布与监听怎么实现”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Spring事件发布与监听怎么实现”吧!

  一、事件监听相关概念介绍

  1、流程分析

  事件:做了什么事。例如,我在写博客,写博客就是一个事件。

  监听器:监听发生事件的组件。例如,我们日常生活中的火灾报警器,监听有没有发生火灾事件。

  在一个完整的事件体系中,除了事件和监听器以外,还应该有3个概念;

  1. 事件源:事件的产生者,任何一个event都必须有一个事件源;

  2. 事件广播器:它是事件和事件监听器之间的桥梁,负责把事件通知给事件监听器;

  3. 事件监听器注册表:就是spring框架为所有的监听器提供了一个存放的地方;

  通过流程图,可以看出它们是如何各司其职的,如下:

Spring事件发布与监听怎么实现

  其实通过流程图,我们很容易发现事件体系就是观察者模式的具体实现,它并没有任何的神秘之处。

  2、流程分析

  结构分析:

  1. 事件类(ApplicaitonEvent):目前spring框架本身仅仅提供了几个事件,很多的事件都是需要自定义的。

  ApplicationEvent唯一的构造函数是ApplicaitonEvent(Object source),通过source指定事件源。 它有两个子类;

  (1)ApplicationContextEvent:容器事件,也就是说事件源是ApplicationContext,框架提供了四个子类,分别代表容器启动,刷新,停止和关闭事件。

  (2)RequestHandleEvent:这是一个与WEB应用相关的事件,当一个请求被处理后,才会产生该事件。

  一般来说,我们都是扩展ApplicationEvent来自定义事件。下面会有栗子。

Spring事件发布与监听怎么实现

  2. 事件监听器接口(ApplicationListener)

  所有的监听器都需要实现该接口,该接口只定义了一个方法:onApplicaitonEvent (E event),该方法接收事件对象,在该方法中编写事件的响应处理逻辑。

Spring事件发布与监听怎么实现

  二、手写模拟事件发布与监听

  注:想直接了解Spring事件监听与发布的,可以跳过这节,但是我建议你还是看一下。

  需求:

  假设现在公司让你开发一个文件操作帮助类 ,

  定义一个文件读写方法 读写某个文件 写到某个类里面去 //但是 有时候可能会需要记录文件读取进度条的需求

  有时候需要进度条 如何实现?

  答案:我们可以采用事件发布与监听。

  事件:文件上传

  事件源:事件在哪里发布的,比如说我们在A类中,发布了事件。那么A类的对象就是事件源。

  监听器:我们编写的FileUploadListener对这个事件进行了监听。并在监听到了当前事件之后,发布事件。

  代码编写:

  

  public class ApplicationEvent {

  }

  

  public interface ApplicationListener {

  void onEvent(E e);

  }

  

  //事件管理器

  public class ListenerManage {

  //保存所有的监听器

  static List> list = new ArrayList<>();

  //添加监听器 注:如果要做的更加优雅,应该做成扫描全局,通过扫描将所有的监听器放入管理器的容器列表,这里为了方便演示就不做复杂了。

  //SpringBoot是从spring的BeanFactory中获取listener

  public static void addListener(ApplicationListener listener) {

  list.add(listener);

  }

  //判断一下 有哪些监听器 监听了这个事件

  public static void publishEvent(ApplicationEvent event) {

  for (ApplicationListener applicationListener : list) {

  //获取ApplicationListener的泛型

  Class typeParameter = (Class) ((ParameterizedType) applicationListener.getClass().getGenericInterfaces()[0]).getActualTypeArguments()[0];

  if (typeParameter.equals(event.getClass())) {

  applicationListener.onEvent(event);

  }

  }

  }

  }

  

  public class FileUploadEvent extends ApplicationEvent {

  private int fileSize;

  private int readSize;

  public FileUploadEvent(int fileSize, int readSize) {

  this.fileSize = fileSize;

  this.readSize = readSize;

  }

  public int getFileSize() {

  return fileSize;

  }

  public void setFileSize(int fileSize) {

  this.fileSize = fileSize;

  }

  public int getReadSize() {

  return readSize;

  }

  public void setReadSize(int readSize) {

  this.readSize = readSize;

  }

  }

  

  public class FileUploadListener implements ApplicationListener {

  @Override

  public void onEvent(FileUploadEvent fileUploadEvent) {

  double molecule = fileUploadEvent.getFileSize();

  double denominator = fileUploadEvent.getReadSize();

  System.out.println("当前文件上传进度百分比:" + (denominator / molecule * 100 + "%"));

  }

  }

  

  public class FileUtil {

  public static int READ_SIZE = 100;

  public static void fileWrite(InputStream is, OutputStream os) throws Exception {

  fileWrite(is, os, null);

  }

  public static void fileWrite(InputStream is, OutputStream os, FileListener fileListener) throws Exception {

  BufferedInputStream bis = new BufferedInputStream(is);

  BufferedOutputStream bos = new BufferedOutputStream(os);

  

  //文件总大小

  int fileSize = is.available();

  //一共读取了多少

  int readSize = 0;

  byte[] readedBytes = new byte[READ_SIZE];

  //控制是否退出

  boolean exit = true;

  while (exit) {

  //文件小于第一次读的大小的时候

  if (fileSize < READ_SIZE) {

  byte[] fileBytes = new byte[fileSize];

  //将缓冲区中的数据写入到字节数组fileBytes中

  bis.read(fileBytes);

  //向文件写入fileBytes数组的内容

  bos.write(fileBytes);

  readSize = fileSize;

  exit = false;

  //当你是最后一次读的时候

  } else if (fileSize < readSize + READ_SIZE) {

  byte[] bytes = new byte[fileSize - readSize];

  readSize = fileSize;

  bis.read(bytes);

  bos.write(bytes);

  exit = false;

  } else {

  bis.read(readedBytes);

  readSize += READ_SIZE;

  bos.write(readedBytes);

  }

  //发布事件

  ListenerManage.publishEvent(new FileUploadEvent(fileSize, readSize));

  if (fileListener != null) {

  fileListener.updateLoad(fileSize, readSize);

  }

  }

  bis.close();

  bos.close();

  }

  }

  

  public class FileReadTest {

  public static void main(String[] args) throws Exception {

  ListenerManage.addListener(new FileUploadListener());

  //这里根据实际情况去设置读写的文件

  File file = new File("F:\\测试写出.txt");

  if (!file.exists()) {

  file.createNewFile();

  }

  //如果需要做进度条功能,再添加一个fileListener参数

  fileWrite(new FileInputStream(new File("F:\\明天要做的事.txt")), new FileOutputStream(file));

  }

  }

  运行结果:

  当前文件上传进度百分比:14.245014245014245%

  当前文件上传进度百分比:28.49002849002849%

  当前文件上传进度百分比:42.73504273504273%

  当前文件上传进度百分比:56.98005698005698%

  当前文件上传进度百分比:71.22507122507122%

  当前文件上传进度百分比:85.47008547008546%

  当前文件上传进度百分比:99.71509971509973%

  当前文件上传进度百分比:100.0%

  三、Spring的时间发布与监听

  我们在上面手动模拟了Spring的时间发布与监听后,看如果上面的例子后,我们使用Spring再写一个事件发布与监听的例子。郑州人流医院 Http://rl.zyfuke.com/

  package com.evan.spring.config;

  import org.springframework.context.annotation.ComponentScan;

  

  @ComponentScan("com")

  public class AppConfig {

  }

  package com.evan.spring.event;

  import org.springframework.context.ApplicationContext;

  import org.springframework.context.event.ApplicationContextEvent;

  import org.springframework.context.event.ContextStartedEvent;

  

  public class WriteBlogEvent extends ApplicationContextEvent {

  String name;

  String address;

  public WriteBlogEvent(ApplicationContext source, String name, String address) {

  super(source);

  this.name = name;

  this.address = address;

  }

  public String getName() {

  return name;

  }

  public String getAddress() {

  return address;

  }

  }

  Spring的事件监听可以基于注解或实现接口。对于同一个事件,如果两个都存在,相当于多个监听器监听一个事件。

  两个监听器内的方法都会执行。

  package com.evan.spring.listener;

  import com.evan.spring.event.WriteBlogEvent;

  import org.springframework.context.ApplicationListener;

  import org.springframework.stereotype.Component;

  

  @Component

  public class WriteBlogListener implements ApplicationListener {

  @Override

  public void onApplicationEvent(WriteBlogEvent writeBlogEvent) {

  String name = writeBlogEvent.getName();

  String address = writeBlogEvent.getAddress();

  System.out.println("基于实现接口:" + name + "在" + address + "写了一篇博客");

  }

  }

  package com.evan.spring.listener;

  import com.evan.spring.event.WriteBlogEvent;

  import org.springframework.context.event.EventListener;

  import org.springframework.stereotype.Component;

  

  @Component

  public class WriteBlogListenerAnnotation {

  @EventListener

  public void annotationListen(WriteBlogEvent writeBlogEvent) {

  String name = writeBlogEvent.getName();

  String address = writeBlogEvent.getAddress();

  System.out.println("基于注解:" + name + "在" + address + "写了一篇博客");

  }

  }

  package com.evan.spring.test;

  import com.evan.spring.config.AppConfig;

  import com.evan.spring.event.WriteBlogEvent;

  import org.springframework.context.annotation.AnnotationConfigApplicationContext;

  

  public class EventTest {

  public static void main(String[] args) {

  AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(AppConfig.class);

  WriteBlogEvent writeBlogEvent = new WriteBlogEvent(ac, "Evan", "家里");

  ac.publishEvent(writeBlogEvent);

  }

  }

  运行结果:

  基于注解:Evan在家里写了一篇博客

  基于实现接口:Evan在家里写了一篇博客

  四、总结

  1、spring 如何得知有哪些监听器?

  通过2个步骤:1.从Bean工厂拿到所有ApplicationListener类型的Bean.

  2.扫描所有带@EventListener

  2、spring如何发布事件?

  大逻辑上通过2个步骤: 1.判断是否有监听器对该事件感兴趣

  2.调用监听器方法

感谢各位的阅读,以上就是“Spring事件发布与监听怎么实现”的内容了,经过本文的学习后,相信大家对Spring事件发布与监听怎么实现这一问题有了更深刻的体会,具体使用情况还需要大家实践验证。这里是编程网,小编将为大家推送更多相关知识点的文章,欢迎关注!

--结束END--

本文标题: Spring事件发布与监听怎么实现

本文链接: https://www.lsjlt.com/news/230215.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Spring事件发布与监听怎么实现
    这篇文章主要讲解了“Spring事件发布与监听怎么实现”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Spring事件发布与监听怎么实现”吧!  一、事件监听相关概念介绍  1、流程分析  事...
    99+
    2023-06-02
  • 详解Spring事件发布与监听机制
    目录一、ApplicationContext 事件机制二、ApplicationListener 监听器三、ApplicationEvent 事件四、自定义事件和监听器五、注解式监听...
    99+
    2022-11-12
  • 解析Spring事件发布与监听机制
    前言 Spring 提供了 ApplicationContext 事件机制,可以发布和监听事件,这个特性非常有用。 Spring 内置了一些事件和监听器,例如在 Spring 容器启...
    99+
    2022-11-12
  • 如何实现Spring事件发布监听、顺序监听和异步监听
    这篇文章给大家分享的是有关如何实现Spring事件发布监听、顺序监听和异步监听的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。1. Spring的事件通知Spring的事件通知本质上就是发布-订阅,即生产者-消费者...
    99+
    2023-06-22
  • Spring的事件发布与监听方式是什么
    本篇内容介绍了“Spring的事件发布与监听方式是什么”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!事件主要代码在org.springfra...
    99+
    2023-07-05
  • Spring事件发布监听,顺序监听,异步监听方式
    目录1. Spring的事件通知2. Spring事件通知使用2.1 Spring的事件2.2 事件监听2.2.1 接口方式实现2.2.2 注解实现2.3 事件发布2.4 Sprin...
    99+
    2022-11-12
  • Spring事件发布与监听机制的用法示例
    小编给大家分享一下Spring事件发布与监听机制的用法示例,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!一、ApplicationContext 事件机制Appl...
    99+
    2023-06-20
  • SpringBoot如何实现ApplicationEvent事件的监听与发布
    这篇文章主要介绍“SpringBoot如何实现ApplicationEvent事件的监听与发布”,在日常操作中,相信很多人在SpringBoot如何实现ApplicationEvent事件的监听与发布问题上存在疑惑,小编查阅了各式资料,整理...
    99+
    2023-07-05
  • 详解SpringBoot实现ApplicationEvent事件的监听与发布
    目录新建SpringBoot项目实现代码pom.xmlApplication.javaTaskPoolConfig.javaEmailDto.javaSendEmailEvent.j...
    99+
    2023-03-08
    SpringBoot ApplicationEvent事件监听发布 SpringBoot ApplicationEvent事件监听 SpringBoot ApplicationEvent事件发布 Sp
  • 使用Spring怎么监听事件
    使用Spring怎么监听事件?相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。一、观察者模式先来看下观察者模式,举个例子警察和军人是观察者,犯罪嫌疑人是被观察者代码实现:定义被观察...
    99+
    2023-06-15
  • JavaWebListener实现事件监听与处理
    目录Listener接口回调Web监听器监听三个作用域创建和销毁监听三个作用域属性状态变更监听HttpSession里面存值的状态变更Listener的应用场景总结在Java Web...
    99+
    2023-05-18
    Java Listener事件监听 Java Listener事件处理
  • Android开发之Button事件实现与监听方法总结
    本文实例总结了Android开发之Button事件实现与监听方法。分享给大家供大家参考,具体如下: 先来介绍Button事件实现的两种方法 main.xml <...
    99+
    2022-06-06
    button 监听 方法 android开发 Android
  • Android开发怎么实现Chip监听及ChipGroup监听
    这篇文章主要介绍“Android开发怎么实现Chip监听及ChipGroup监听”,在日常操作中,相信很多人在Android开发怎么实现Chip监听及ChipGroup监听问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对...
    99+
    2023-07-02
  • 详解SpringBoot实现事件同步与异步监听
    目录简介事件监听简述实例同步监听(无序)同步监听(有序)异步监听(无序)简介 说明 本文用示例介绍SpringBoot中的事件的用法及原理。 事件监听简述 事件的发布与监听从属于观察...
    99+
    2022-11-13
  • JavaScript怎么利用发布订阅模式编写事件监听函数
    这篇“JavaScript怎么利用发布订阅模式编写事件监听函数”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“JavaScri...
    99+
    2023-07-06
  • Vue组件事件触发和监听实现源码解析
    目录正文Vue 的事件触发和监听源码分析ononceemitoff动手实现总结正文 通常我们在使用Vue的时候,会使用$emit和$on来触发和监听事件,但是有没有思考是如何实现的呢...
    99+
    2022-12-22
    Vue 组件事件触发监听 Vue 组件触发监听
  • Android中的监听触摸事件怎么在Fragment中实现
    本篇文章为大家展示了Android中的监听触摸事件怎么在Fragment中实现,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。activity的触摸事件 @Override public boolea...
    99+
    2023-05-31
    android fragment roi
  • springboot应用服务启动事件的监听怎么实现
    本篇内容主要讲解“springboot应用服务启动事件的监听怎么实现”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“springboot应用服务启动事件的监听怎么实现”吧!一、简介Spring B...
    99+
    2023-06-29
  • Vue怎么通过监听滚动事件实现动态锚点
    本文小编为大家详细介绍“Vue怎么通过监听滚动事件实现动态锚点”,内容详细,步骤清晰,细节处理妥当,希望这篇“Vue怎么通过监听滚动事件实现动态锚点”文章能帮助大家解决疑惑,下面跟着小编的思路慢慢深入,一起来学习新知识吧。具体效果如下:一、...
    99+
    2023-07-04
  • Vue.js父组件$on无法监听子组件$emit触发事件怎么办
    这篇文章主要为大家展示了“Vue.js父组件$on无法监听子组件$emit触发事件怎么办”,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带领大家一起研究并学习一下“Vue.js父组件$on无...
    99+
    2022-10-19
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作