Spring如何控制Bean的加载顺序

前言

正常情况下,Spring 容器加载 Bean 的顺序是不确定的,那么我们如果需要按顺序加载 Bean 时应如何操作?本文将详细讲述我们如何才能控制 Bean 的加载顺序。


场景

我创建了 4 个 Class 文件,分别命名为

  1. FirstInitialization

  2. SecondInitialization

  3. ThirdInitialization

  4. ForthInitialization

我希望这 4 个类按照 1、2、3、4 的顺序加载。

如下图,直接加载的话,顺序是 1、4、2、3,并不能达到要求。

如何控制

注意:网上很多文章说Order注解或Ordered接口可以控制 Bean 的加载顺序,其是并不能,它们的作用是定义 Spring IOC 容器中 Bean 定义类的执行顺序的优先级,并不是定义加载顺序。

使用@DependsOn 注解

在需要调整顺序的类上依次加@DependsOn注解,缺点是类过多的时候需要一个个加注解,且不好维护

@Component
public class FirstInitialization {@PostConstructpublic void init(){System.out.println("我是第一个加载!");}}

@Component
@DependsOn("firstInitialization")
public class SecondInitialization {@PostConstructpublic void init(){System.out.println("我是第二个加载!");}}

@Component
@DependsOn("secondInitialization")
public class ThirdInitialization {@PostConstructpublic void init(){System.out.println("我是第三个加载!");}}

@Component
@DependsOn("thirdInitialization")
public class ForthInitialization {@PostConstructpublic void init(){System.out.println("我是第四个加载!");}}

执行结果如下

基于 ApplicationContextInitializer 接口

接口简介

这里我简单介绍一个这个接口的用处, 等到整理到相关源码的时候再详细介绍。

ApplicationContextInitializer接口是在 Spring 容器刷新之前执行的一个回调函数。

执行时机:

  1. Spring 内部执行ConfigurableApplicationContext#refresh()方法前;

  2. SpringBoot 执行run()方法前。

一般有什么用呢?

在 SpringBoot 应用中 Classpath 上会有很多 jar 包,有些 jar 包需要在refresh()调用前对应用上下文做一些初始化动作,因此会提供ApplicationContextInitializer接口的实现类,放在如下图的文件中,这样会被SpringApplication#initialize发现,然后完成对应初始化。

实现步骤

首先创建一个类继承ApplicationContextInitializer接口。

public class MyApplicationContextInitializer implements ApplicationContextInitializer {@Overridepublic void initialize(ConfigurableApplicationContext applicationContext) {//将自定义的BeanFactoryPostProcessor实现类保存到ApplicationContext中applicationContext.addBeanFactoryPostProcessor(new MyBeanFactoryPostProcessor());}
}

创建`META-INF/spring.factories`文件。

自定义`BeanDefinitionRegistryPostProcessor`。

/*** BeanFactoryPostProcessor的子类* 允许开发人员在Bean定义注册之前和之后对BeanDefinition进行自定义处理,例如添加,修改或删除Bean定义等。*/
public class MyBeanFactoryPostProcessor implements BeanDefinitionRegistryPostProcessor {// 初始化需要排序的类,这里要保证插入顺序只能用LinkedHashMapprivate static final Map<String, Class> ORDER_BEAN_MAP = new LinkedHashMap<>() {{put("firstInitialization", FirstInitialization.class);put("secondInitialization", SecondInitialization.class);put("thirdInitialization", ThirdInitialization.class);put("forthInitialization", ForthInitialization.class);}};@Overridepublic void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {Optional.ofNullable(ORDER_BEAN_MAP.keySet()).orElse(new HashSet<>()).stream().forEach(beanName -> {// 初始化一个 Bean 定义AbstractBeanDefinition beanDefinition = BeanDefinitionBuilder.genericBeanDefinition().getBeanDefinition();// 按顺序注册每个BeanbeanDefinition.setBeanClass(ORDER_BEAN_MAP.get(beanName));registry.registerBeanDefinition(beanName, beanDefinition);});}
}

执行结果如下

文章转载自:fuxing.

原文链接:https://www.cnblogs.com/fuxing/p/18181623

体验地址:引迈 - JNPF快速开发平台_低代码开发平台_零代码开发平台_流程设计器_表单引擎_工作流引擎_软件架构

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/9587.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

python数据分析——数据的选择和运算

数据的选择和运算 前言一、数据选择NumPy的数据选择一维数组元素提取示例 多维数组行列选择、区域选择示例 花式索引与布尔值索引布尔索引示例一示例二 花式索引示例一示例二 Pandas数据选择Series数据获取DataFrame数据获取列索引取值示例一示例二 取行方式示例loc() 方法示例…

人脸图像生成(DCGAN)

一、理论基础 1.什么是深度卷积对抗网络&#xff08;Deep Convolutional Generative Adversarial Network&#xff0c;&#xff09; 深度卷积对抗网络&#xff08;Deep Convolutional Generative Adversarial Network&#xff0c;DCGAN&#xff09;是一种生成对抗网络&#xf…

网工内推 | 软件测试工程师,有软考中、高级认证优先

01 上海碧蔓智能科技有限公司 招聘岗位&#xff1a;软件测试工程师 职责描述&#xff1a; 1、负责软件产品的测试工作&#xff0c;对测试进度和测试质量负责&#xff1b; 2、参与业务需求、设计方案的讨论&#xff0c;负责编写测试方案、测试计划、测试用例&#xff0c;搭建测…

LMDeploy笔记

随谈模型部署 模型部署包含的内容很多&#xff0c;来聊聊。 访存bottleneck 首先&#xff0c;基于transformer的计算是访存密集型任务。 so? 过去&#xff0c;我们表达模型的性能&#xff0c;通常会用ops&#xff0c;macs这些指标,也计算量来衡量模型的推理时间&#xff…

JSP ssm 智能水表管理myeclipse开发mysql数据库springMVC模式java编程计算机网页设计

一、源码特点 JSP ssm 智能水表管理系统是一套完善的web设计系统&#xff08;系统采用SSM框架进行设计开发&#xff0c;springspringMVCmybatis&#xff09;&#xff0c;对理解JSP java编程开发语言有帮助&#xff0c;系统具有完整的源代码和数据库&#xff0c;系统主要采…

Vue自定义封装音频播放组件(带拖拽进度条)

Vue自定义封装音频播放组件&#xff08;带拖拽进度条&#xff09; 描述 该款自定义组件可作为音频、视频播放的进度条&#xff0c;用于控制音频、视频的播放进度、暂停开始、拖拽进度条拓展性极高。 实现效果 具体效果可以根据自定义内容进行位置调整 项目需求 有播放暂停…

使用Python实现DataFrame中奇数列与偶数列的位置调换

目录 一、引言 二、背景知识 三、问题描述 四、解决方案 五、案例分析与代码实现 六、技术细节与注意事项 七、扩展与应用 八、封装为函数 九、错误处理与健壮性 十、性能优化 十一、总结与展望 一、引言 在数据处理和分析中&#xff0c;数据框&#xff08;DataFra…

16地标准化企业申请!安徽省工业和信息化领域标准化示范企业申报条件

安徽省工业和信息化领域标准化示范企业申报条件有哪些&#xff1f;合肥市 、黄山市 、芜湖市、马鞍山、安庆市、淮南市、阜阳市、淮北市、铜陵市、亳州市、宣城市、蚌埠市、六安市 、滁州市 、池州市、宿州市企业申报安徽省工业和信息化领域标准化示范企业有不明白的可在下文了…

药物代谢动力学学习笔记

一、基本概念 二、经典房室模型 三、非线性药物代谢动力学 四、非房室模型 五、药代动力学与药效动力学 六、生物等效性评价 七、生物样品分析方法 基本概念 生物样品&#xff1a;生物机体的全血、血浆、血清、粪便、尿液或其他组织的样品 特异性&#xff0c;specificity&…

信息技术自主可控的意义,针对国产化替换,服务器虚拟化或比公有云更具优势

我们之前在文章《博通收购VMware后&#xff0c;经销商和用户如何应对&#xff1f;新出路&#xff1a;虚拟化国产替代&#xff0c;融入信创云生态》中提到&#xff1a; 从信创整体发展和政策标准来看&#xff0c;供应商必须满足两个条件&#xff1a;一是融入国产信息技术生态&am…

FDM3D打印系列——系列模型的身高比例问题

大家好&#xff0c;我是阿赵。   最近又打印了一个拳皇的角色手办&#xff0c;不过在这个过程中&#xff0c;发现了一个不同角色之前比例的问题&#xff0c;和大家分享一下。   这个就是这次打印的模型&#xff0c;估计大家都很熟悉&#xff1a; 没错&#xff0c;就是拳皇…

gif压缩大小但不改变画质怎么做?分享5个压缩GIF原理~

GIF&#xff08;图形互换格式&#xff09;是网络上广泛使用的一种图像格式&#xff0c;因其支持动画而备受欢迎。然而&#xff0c;随着动画越来越复杂和高分辨率&#xff0c;GIF 文件大小也随之增加&#xff0c;可能导致加载速度变慢和带宽消耗增加。在这篇文章中&#xff0c;我…

反着用scaling law验证数据:群聊场景指代消歧

本文作者&#xff1a;白牛 我们之前开源了 LLM 群聊助手茴香豆&#xff08;以下简称豆哥&#xff09;&#xff0c;它的特点是&#xff1a; 设计了一套拒答 pipeline&#xff0c;实用于群聊场景。能够有效抵抗各种文本攻击、过滤无关话题&#xff0c;累计面对 openmmlab 数千用…

Python专题:六、循环语句(1)

补充知识 代码的注释 #描述性文字 阅读代码的人更好的理解代码 while循环语句 x<100条件控制语句&#xff0c;Totalx,Total自增加x&#xff0c;x1&#xff0c;x自增加1&#xff0c;x<100此条件满足时&#xff0c;执行while循环&#xff0c;当x101时&#xff0c;x101条…

# 从浅入深 学习 SpringCloud 微服务架构(十五)

从浅入深 学习 SpringCloud 微服务架构&#xff08;十五&#xff09; 一、SpringCloudStream 的概述 在实际的企业开发中&#xff0c;消息中间件是至关重要的组件之一。消息中间件主要解决应用解耦&#xff0c;异步消息&#xff0c;流量削锋等问题&#xff0c;实现高性能&…

【图像增强(空域)】基于直方图增强的图像增强及Matlab仿真

1. 摘要 图像的灰度直方图表示灰度图像中具有每种灰度像素的个数&#xff0c;反映了图像中每种灰度级出现的频率&#xff0c;是图像的基本统计特征之一。直方图均衡方法因为其有效性和简单性已成为图像对比度增强的最常用的方法。其基本思想是根据输入图像的灰度概率分布来确定…

【全开源】Java外卖霸王餐免费吃外卖小程序+APP+公众号+H5多端霸王餐源码

一、特色功能 霸王餐活动管理&#xff1a;允许商家发布和管理霸王餐活动&#xff0c;包括设置活动时间、具体优惠、活动规则等。用户参与与浏览&#xff1a;用户可以在小程序中浏览霸王餐活动列表&#xff0c;查看活动的详情信息&#xff0c;如商品或服务的免费赠送、活动规则…

原生微信小程序canvas签名功能

半个月前百度搜出来的&#xff0c;没存书签现在不知道是哪篇文章了&#xff0c;再搜也没搜出来那篇文章&#xff0c;还好当时把代码复制到本地跑了一下&#xff0c;现在再发csdn存一下。 sign.js Page({data: {ctx: null,width: null,height: null,drawCount: 0,drawState: &…

查找本机上的WIFI并查看密码。

在命令行模式下&#xff1a; 1。WIN 键 R&#xff0c;输入CMD&#xff0c;回车确认 2。在搜索框输入CMD&#xff0c;回车确认 以上的方法都可以打开命令行模式。也称终端&#xff0c;或者DOS模式。 查找本机上的WIFI密码&#xff0c;命令行如下&#xff1a; 首先&#xff…

汉诺塔问题和爬楼梯(递归)

感谢大佬的光临各位&#xff0c;希望和大家一起进步&#xff0c;望得到你的三连&#xff0c;互三支持&#xff0c;一起进步 个人主页&#xff1a;LaNzikinh-CSDN博客 c语言基础_LaNzikinh篮子的博客-CSDN博客 文章目录 一.爬楼梯问题二.汉诺塔问题总结 一.爬楼梯问题 假设你正…