您当前的位置:首页 > 电脑百科 > 程序开发 > 框架

SpringEvent的应用

时间:2022-08-08 14:40:01  来源:  作者:小柴学Java

前言

该文章是我学习使用SpirngEvent的过程,现在只写了SpringEvent的应用,后续会写一篇从源码关注SpringEvent的实现过程。

SpringEvent的介绍

SpringEvent在我认为是一个解决业务解耦的办法,运用了观察者模式,用于 当一个业务的更改后,需要改变其他业务的状态 。例如一个商品的下单,需要修改商品的库存,以及商家的消息发送等等。之前我做这种业务解耦的时候,使用的时消息队列进行解耦,但如果只是为了解耦而整合了消息队列,就有点大了,我认为,可以使用此方式需要满足下面的条件:

  • 当做完业务的时候,不清楚有多少个子业务要进行更改,例如安防设备的报警,初期可能只是发送消息到持有设备的用户,页面显示报警状态,后期或许会涉及到同步到其他平台业务、和其他安防设备产生连锁报警业务等等。

SpringEvent的应用

环境配置

JDK8

Spring boot 2.6.10

业务场景

当电脑启动的时候,电脑的自启程序需要启动,程序的服务也需要启动等等。

实现

创建ComputerStartEvent电脑启动事件类

/** * 电脑启动事件类 */public class ComputerStartEvent extends ApplicationEvent {    private ComputerEntity computerEntity;    public ComputerEntity getComputerEntity() {        return computerEntity;    }    public ComputerStartEvent(ComputerEntity source) {        super(source);        this.computerEntity=source;    }}复制代码

创建AutoStartupSoftwareListener自启软件启动监听类

/**** 自启软件启动监听类*/@Componentpublic class AutoStartupSoftwareListener implements ApplicationListener<ComputerStartEvent> {    @Override    public void onApplicationEvent(ComputerStartEvent event) {        ComputerEntity computer=event.getComputerEntity();        System.out.println("电脑"+computer.getName()+"的自启软件正在进行");    }}复制代码

创建ProgramServiceStartupListener程序服务启动监听类

/** * 程序服务启动监听类 */@Componentpublic class ProgramServiceStartupListener implements ApplicationListener<ComputerStartEvent> {    @Override    public void onApplicationEvent(ComputerStartEvent event) {        ComputerEntity computer=event.getComputerEntity();        System.out.println("电脑"+computer.getName()+"的程序服务正在启动");    }}复制代码

客户端代码

poublic class ComputerService {    @Resource    private ApplicationEventPublisher applicationEventPublisher;    public void computerStart() {        ComputerEntity computer=new ComputerEntity();;        computer.setComputerId("dafdasf");        computer.setName("电脑A");        // 电脑启动操作        System.out.println(computer.getName()+"电脑启动了");                //发布电脑启动事件        applicationEventPublisher.publishEvent(new ComputerStartEvent(computer));    }}复制代码

效果

 

异步实现

目前有两种方式可以实现异步,

  • 一种是使用@EnableAsync和@Async启动异步。
  • 一种是给Springboot的默认实现 SimpleAsyncEventMulticaster 类中的 taskExecutor 字段赋值一个线程池。

一、使用@EnableAsync和@Async启动异步

下面为了演示异步的效果,自启软件的监听类不使用异步,程序服务的监听类使用异步,然后每个方法打印当前线程的Id。

AutoStartupSoftwareListener自启软件启动监听类

/*** 自启软件启动监听类*/@Componentpublic class AutoStartupSoftwareListener implements ApplicationListener<ComputerStartEvent> {    @Override    public void onApplicationEvent(ComputerStartEvent event) {        ComputerEntity computer=event.getComputerEntity();        System.out.println("电脑"+computer.getName()+"的自启软件正在进行");        //打印线程Id        System.out.println("AutoStartupSoftwareListener监听线程id:"+Thread.currentThread().getId());    }}复制代码

ProgramServiceStartupListener程序服务启动监听类

/** * 程序服务启动监听类 */@EnableAsync@Componentpublic class ProgramServiceStartupListener implements ApplicationListener<ComputerStartEvent> {    @Override    @Async    public void onApplicationEvent(ComputerStartEvent event) {        ComputerEntity computer=event.getComputerEntity();        System.out.println("电脑"+computer.getName()+"的程序服务正在启动");        //打印线程Id        System.out.println("ProgramServiceStartupListener监听线程id:"+Thread.currentThread().getId());    }}复制代码

客户端代码

poublic class ComputerService {    @Resource    private ApplicationEventPublisher applicationEventPublisher;    public void computerStart() {        ComputerEntity computer=new ComputerEntity();;        computer.setComputerId("dafdasf");        computer.setName("电脑A");        // 电脑启动操作        System.out.println(computer.getName()+"电脑启动了");                //发布电脑启动事件        applicationEventPublisher.publishEvent(new ComputerStartEvent(computer));        //打印线程Id        System.out.println("computerStart方法线程id:"+Thread.currentThread().getId());    }}复制代码

效果

 

异步启用成功

二、给SimpleAsyncEventMulticaster类中的taskExecutor字段赋值线程池

创建SimpleAsyncEventMulticaster继承SimpleApplicationEventMulticaster

//需要指定下beanName@Component("applicationEventMulticaster")public class SimpleAsyncEventMulticaster extends SimpleApplicationEventMulticaster {    public SimpleAsyncEventMulticaster(){        ThreadPoolTaskExecutor taskExecutor=new ThreadPoolTaskExecutor();        taskExecutor.initialize();        taskExecutor.setCorePoolSize(5);        taskExecutor.setMaxPoolSize(100);        taskExecutor.setQueueCapacity(1000);        taskExecutor.setThreadNamePrefix("test-async");        setTaskExecutor(taskExecutor);    }}复制代码

效果

 

两种异步的区别

如果给
SimpleAsyncEventMulticaster 的 taskExecutor 字段赋值线程池,所有监听类的执行都会是异步的,如果想要个别的任务执行是异步的话,需要重写
SimpleAsyncEventMulticaster 的 multicastEvent 方法,而使用@Async则不会,这也是为啥推荐的都是@Async方式实现异步。

总结

本文章介绍了SpringEvent和应用条件以及实例,这里没有写源码的解析,因为比较长,上述内容如果有误人子弟的地方,望在评论区留言。



Tags:SpringEvent   点击:()  评论:()
声明:本站部分内容及图片来自互联网,转载是出于传递更多信息之目的,内容观点仅代表作者本人,不构成投资建议。投资者据此操作,风险自担。如有任何标注错误或版权侵犯请与我们联系,我们将及时更正、删除。
▌相关推荐
当我准备用SpringEvent优雅的解耦时,连续两个bug把我搞懵了
日常开发中,我们有时会使用SpringEvent对业务解耦,使我们的代码更加高内聚低耦合,不过如果对其运行原理不清楚,那么在使用的过程中,一不留神就会出现一些bug。今天我们回顾一下Sp...【详细内容】
2022-12-08  Search: SpringEvent  点击:(465)  评论:(0)  加入收藏
SpringEvent的应用
前言该文章是我学习使用SpirngEvent的过程,现在只写了SpringEvent的应用,后续会写一篇从源码关注SpringEvent的实现过程。SpringEvent的介绍SpringEvent在我认为是一个解决业...【详细内容】
2022-08-08  Search: SpringEvent  点击:(436)  评论:(0)  加入收藏
▌简易百科推荐
Qt与Flutter:在跨平台UI框架中哪个更受欢迎?
在跨平台UI框架领域,Qt和Flutter是两个备受瞩目的选择。它们各自具有独特的优势,也各自有着广泛的应用场景。本文将对Qt和Flutter进行详细的比较,以探讨在跨平台UI框架中哪个更...【详细内容】
2024-04-12  刘长伟    Tags:UI框架   点击:(7)  评论:(0)  加入收藏
Web Components实践:如何搭建一个框架无关的AI组件库
一、让人又爱又恨的Web ComponentsWeb Components是一种用于构建可重用的Web元素的技术。它允许开发者创建自定义的HTML元素,这些元素可以在不同的Web应用程序中重复使用,并且...【详细内容】
2024-04-03  京东云开发者    Tags:Web Components   点击:(11)  评论:(0)  加入收藏
Kubernetes 集群 CPU 使用率只有 13% :这下大家该知道如何省钱了
作者 | THE STACK译者 | 刘雅梦策划 | Tina根据 CAST AI 对 4000 个 Kubernetes 集群的分析,Kubernetes 集群通常只使用 13% 的 CPU 和平均 20% 的内存,这表明存在严重的过度...【详细内容】
2024-03-08  InfoQ    Tags:Kubernetes   点击:(23)  评论:(0)  加入收藏
Spring Security:保障应用安全的利器
SpringSecurity作为一个功能强大的安全框架,为Java应用程序提供了全面的安全保障,包括认证、授权、防护和集成等方面。本文将介绍SpringSecurity在这些方面的特性和优势,以及它...【详细内容】
2024-02-27  风舞凋零叶    Tags:Spring Security   点击:(62)  评论:(0)  加入收藏
五大跨平台桌面应用开发框架:Electron、Tauri、Flutter等
一、什么是跨平台桌面应用开发框架跨平台桌面应用开发框架是一种工具或框架,它允许开发者使用一种统一的代码库或语言来创建能够在多个操作系统上运行的桌面应用程序。传统上...【详细内容】
2024-02-26  贝格前端工场    Tags:框架   点击:(52)  评论:(0)  加入收藏
Spring Security权限控制框架使用指南
在常用的后台管理系统中,通常都会有访问权限控制的需求,用于限制不同人员对于接口的访问能力,如果用户不具备指定的权限,则不能访问某些接口。本文将用 waynboot-mall 项目举例...【详细内容】
2024-02-19  程序员wayn  微信公众号  Tags:Spring   点击:(43)  评论:(0)  加入收藏
开发者的Kubernetes懒人指南
你可以将本文作为开发者快速了解 Kubernetes 的指南。从基础知识到更高级的主题,如 Helm Chart,以及所有这些如何影响你作为开发者。译自Kubernetes for Lazy Developers。作...【详细内容】
2024-02-01  云云众生s  微信公众号  Tags:Kubernetes   点击:(58)  评论:(0)  加入收藏
链世界:一种简单而有效的人类行为Agent模型强化学习框架
强化学习是一种机器学习的方法,它通过让智能体(Agent)与环境交互,从而学习如何选择最优的行动来最大化累积的奖励。强化学习在许多领域都有广泛的应用,例如游戏、机器人、自动驾...【详细内容】
2024-01-30  大噬元兽  微信公众号  Tags:框架   点击:(72)  评论:(0)  加入收藏
Spring实现Kafka重试Topic,真的太香了
概述Kafka的强大功能之一是每个分区都有一个Consumer的偏移值。该偏移值是消费者将读取的下一条消息的值。可以自动或手动增加该值。如果我们由于错误而无法处理消息并想重...【详细内容】
2024-01-26  HELLO程序员  微信公众号  Tags:Spring   点击:(95)  评论:(0)  加入收藏
SpringBoot如何实现缓存预热?
缓存预热是指在 Spring Boot 项目启动时,预先将数据加载到缓存系统(如 Redis)中的一种机制。那么问题来了,在 Spring Boot 项目启动之后,在什么时候?在哪里可以将数据加载到缓存系...【详细内容】
2024-01-19   Java中文社群  微信公众号  Tags:SpringBoot   点击:(91)  评论:(0)  加入收藏
相关文章
    无相关信息
站内最新
站内热门
站内头条