当前位置: 首页 > news >正文

SpringBoot的自动装配原理

一、@SpringBootConfiguration注解的作用

                @SpringBootApplication注解是SpringBoot项目的核心注解,加在启动引导类上。点击进去可以发现@SpringBootApplication注解是一个组合注解。其中@SpringBootConfiguration@EnableAutoConfiguration是由Spring提供的,剩下的注解是由JDK提供的。对于SpringBoot项目,我们重点分析@SpringBootConfiguration和@EnableAutoConfiguration注解

1.1、@SpringBootConfiguration表示启动引导类是一个配置类

        点击@SpringBootConfiguration注解进去可以发现@SpringBootConfiguration注解也是一个组合注解,并且继承了@Configuration注解,说明@SpringBootApplication注解间接继承了

@Configuration注解。

        @Configuration注解又加在了启动引导类上面,说明启动引导类是一个配置类,配置类中加了@Bean注解的方法的返回值会放入Spring的容器中。

代码演示:

启动引导类中添加@Bean注解的方法

package com.itboy;import com.itboy.Import.MyImportSeletor;
import com.itboy.pojo.User;
import org.example.config.BrandAutoConfiguration;
import org.example.config.UserAutoConfiguration;
import org.example.pojo.Brand;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.ServletComponentScan;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Import;/*** */
@SpringBootApplicationpublic class SpringBootPlusApplication {public static void main(String[] args) {ConfigurableApplicationContext app = SpringApplication.run(SpringBootPlusApplication.class, args);User user = app.getBean(User.class);System.out.println("user = " + user);}@Beanpublic User testUser(){return new User();}}

        运动程序,发现可以从容器中获得User对象,说明添加了@Bean注解的方法的返回值放到了Spring容器中。

所以@SpringBootConfiguration注解的第一个作用就是将启动引导类变成配置类

1.2、 @SpringBootConfiguration可以让测试类能够找到启动引导类

        注释掉启动引导类上面的@SpringBootApplication注解,然后启动@SpringBootTest测试类中的测试方法,会发现报错。

Unable to find a @SpringBootConfiguration 

说明 @SpringBootTest测试类中的测试方法会去找@SpringBootConfiguration注解。

此时需要手动指定启动引导类才能解决报错问题

 

1.3、总结 

 @SpringBootConfiguration注解的作用有:

1、表示启动引导类是一个配置类,因为相当于@SpringBootApplication注解间接继承了@Configuration注解。

2、 让测试类能够找到启动引导类,具体的看1.2中的内容。

二、@Import注解的作用 

 通过@Import注解中的导入器我们可以指定配置类。

我们在pom.xml配置文件中添加创建的模块

创建的模块结构如下图:

 

创建的模块中存在两个配置类UserAutoConfigurationBrandAutoConfiguration 

                                  

 

 

创建的模块和我们主模块之间的位置关系:

 

        所以创建的模块肯定不在spring_boot项目启动引导类的包及其子包中。 所以在spring_boot项目的容器对象中肯定不能获取到创建的模块中的User和brand对象。

        但是在启动引导类上添加@Import注解就能获取到User和brand对象。

        通过@Import注解中的导入器能指定配置类有哪些,@Import注解中的值相当于导入器,这里的MyImportSeletor.class是我自定义的导入器

 

        导入器需要实现ImportSelector接口,并重写selectImports方法,返回值为字符串数组,里面的值为配置类的全限定名,通过返回值就能确定配置类有哪些

        再找到配置类中加了@Bean注解的方法,方法的返回值就会放入spring的容器中。就完成了自动装配的工程。

总结

1、@Import注解可以通过导入器指定配置类。

2、@Import注解中的值是导入器,通过导入器我们可以指定配置类。

3、配置类中加了@Bean注解的方法的返回值就会放到spring容器中,从而实现自动装配。

三、@EnableAutoConfiguration注解的作用 

        @EnableAutoConfiguration注解是组合注解,继承了@Import注解。

        

        通过二中分析我们知道可以通过@Import注解中的导入器找到配置类,这里的AutoConfigurationImportSelector.class就是SpringBoot定义的导入器,所以继续点击导入器。

        发现AutoConfigurationImportSelector.class导入器中存在selectImports方法,并且方法返回值为字符串数组,与二中刚才的分析保持一致,所以这个selectImports方法就是指定配置类

 

        if的条件判断是返回没有导入的情况,所以else里面的逻辑才是指定配置类。 

        接着点击selectImports方法中的getAutoConfigurationEntry方法,再点击getAutoConfigurationEntry方法中的getCandidateConfigurations方法        

        

        接着点击 getCandidateConfigurations方法中的loadFactoryNames方法

    

 

         接着点击loadFactoryNames方法中的loadSpringFactories方法

        最后发现读取的是META-INF文件夹里面的spring.factorie文件 

 

总结:

1、 @EnableAutoConfiguration注解的作用是完成SpringBoot项目的自动装配。

2、会去读取META-INF文件夹里面的spring.factorie文件。

3、spring.factorie文件中定义了指定的配置类,找到配置类,并把配置类中加了@Bean注解的方法的返回值放入Spring容器就完成了自动装配。

四、自动装配的条件选择

4.1、SpringBoot自带的Starter和第三方Starter

        SpringBoot提供的Starter是以spring-boot-starter开头的,例如spring-boot-starter-webspring-boot-starter-test

                

        第三方提供的starter一般是以spring-boot-starter为结尾的。例如:mybatis-spring-boot-starter

       

 

4.2、通过在External Libraries中找到对应的jar包

        可以发现第三方Starter都会有 META-INF文件夹,并且META-INF文件夹里面肯定也会有spring.factorie文件。下面是mybatisspring.factorie文件里面的内容。

        

org.springframework.boot.autoconfigure.EnableAutoConfiguration是key值,固定的写法。

里面的value值定义了配置类,mybatis定义的配置类有:

MybatisLanguageDriverAutoConfiguration

MybatisAutoConfiguration

MybatisDependsOnDatabaseInitializationDetector

 4.3、ConditionalOn.....注解决定了哪些方法返回值放入Spring容器中

        打开4.2中找到的MybatisLanguageDriverAutoConfiguration配置类。

        可以发现 MybatisLanguageDriverAutoConfiguration类肯定被@Configuration注解定义了,那是不是这个类所有加了@Bean注解的方法的返回值都会放入Spring容器中完成自动装配呢?

         可以发现MybatisLanguageDriverAutoConfiguration类中的很多方法上面加了类似@ConditionalOnClass、@ConditionalOnMissingBean等注解,都是限制条件,所以并不是所有的加了@Bean注解的方法的返回值都会放入Spring容器中。

 

 

  总结:

1、 指定的配置类中并不是所有的加了@Bean注解的方法的返回值都会放入Spring容器中。

2、 @ConditionalOnClass、@ConditionalOnMissingBean等注解,都是限制条件。

 

五、自动装配原理总结

        通过@EnableAutoConfiguration注解,会去找到第三方jar包中META-INF文件夹里面的spring.factorie文件。

        spring.factorie文件里面指定了配置类,再找到配置类中加了@Bean注解的方法,再找到能通过@ConditionalOnClass、@ConditionalOnMissingBean等注解的限制条件后,就会将方法返回值放入Spring的容器中。

相关文章:

SpringBoot的自动装配原理

一、SpringBootConfiguration注解的作用 SpringBootApplication注解是SpringBoot项目的核心注解,加在启动引导类上。点击进去可以发现SpringBootApplication注解是一个组合注解。其中SpringBootConfiguration和EnableAutoConfiguration是由Spring提供的,剩下的注解是由JDK提供的…...

嵌入式驱动开发需要会哪些技能?

嵌入式驱动开发是指在嵌入式系统中编写驱动程序,实现设备与计算机之间的通信。嵌入式驱动开发是指编写设备驱动程序,实现设备与计算机之间的通信。以下是一些嵌入式驱动开发的具体操作方法: 1)了解硬件设备结构:在进行嵌入式驱动…...

Leetcode:二分搜索树层次遍历

题目: 给你二叉树的根节点 root ,返回其节点值的 层序遍历 。 (即逐层地,从左到右访问所有节点)。 示例: 示例 1: 输入:root [3,9,20,null,null,15,7] 输出:[[3],[9,…...

【fabric.js】toDataURL 性能问题、优化

必要解释:最好看完。。省流版的话,toDataURL 的 multiplier参数不要设置超过500; 情景:在做某些功能的时候涉及到图形的预览,预览的时候是导出为40*40 像素的图片,当碰到某些图形非常小的时候,…...

基于Grafana+Prometheus搭建可视化监控系统实践

基本介绍 Grafana:一个监控仪表系统,可以根据提供的监控数据,生产可视化仪表盘,同时也具有告警通知功能。这里的监控数据来源,目前主要以Prometheus为主(也支持其它数据源),每次展现…...

选择排序(堆排序和topK问题)

选择排序 每一次从待排序的数据元素中选出最小(或最大)的一个元素,存放在序列的起始位置,直到全部待排序的数据元素排完 。 如果我们用扑克牌来举例,那么选择排序就像是提前已经把所有牌都摸完了,而再进行牌…...

webpack tree shaking 摇树原理

Tree-shaking 是指在打包过程中通过静态分析,识别并删除未使用的代码,以减小最终输出文件的大小。Webpack 通过内置的 UglifyJS 插件或者 Terser 插件来实现 Tree-shaking。下面是简要的 webpack Tree-shaking 的原理: 标记未使用的代码&…...

开源模型应用落地-业务整合篇(三)

一、前言 在之前的两篇文章中,我们学习了如何构建基本的即时消息(IM)功能。今天,我们将进一步将IM模块与AI服务进行连接,实现用户提问并由模型进行回答,最后将结果展示在用户界面上。 二、术语 2.1. Spring Boot 是一个用于快速构建基于Spring框架的Java应用程序的开源框…...

js打地鼠

文章目录 1实现效果2代码实现 1实现效果 游戏难度:简单,一般,困难,噩梦(控制setInterval的time参数) 按钮功能:结束(可以通过修改gameScore的值来修改判定结束的分数)&am…...

计算机网络体系架构认知--网络协议栈

文章目录 一.计算机网络分层架构各协议层和计算机系统的联系从整体上理解计算机网络通信计算机网络通信的本质 二.Mac地址,IP地址和进程端口号三.局域网通信与跨局域网通信局域网通信跨局域网通信全球互联的通信脉络 四.网络编程概述 一.计算机网络分层架构 实现计算机长距离网…...

Ubuntu 22.04 安装tomcat

tomcat是常用的Java服务容器,这篇文章我们就来讲讲如何安装它。 更新软件包 首先是更新软件包,这是最常规的操作 sudo apt update 然后是开始安装,不多一会就可以安装好了 sudo apt install tomcat9 然后看一下状态 sudo systemctl status tomcat9 发现虽然启动了,但…...

记录:Ubuntu 18.04 X86 上通过CMake 指定编译器工具链交叉编译。

最好是通过 cmake 命令行来设置,要不然你只有在 CMakeFiles.txt 里面自己写判断语句了。 要用 cmake 交叉编译,必须设置连接器,要不然会使用当前系统的 ld,就是 /usr/bin/ld。 但是其它平台是不会ld上的,elf格式都不…...

requests,js逆向练习

自上而下排除jquery源码,点进去utils 发现第一次请求是getTime 再次运行此断点才是登录,这个时候密码已经被加密了 查看上级js页面,发现加密函数 进去看函数加密过程 得到结果RSA python代码 import base64 import jsonimport requests f…...

Chrome 插件调试

http://blog.haoji.me/chrome-plugin-develop.html#te-bie-zhu-yi-background-de-bao-cuo 手把手:Chrome浏览器开发系列(四):调试我们开发的插件 - 掘金...

云轴科技ZStack成为交通运输业上云用云推进中心首批成员单位

近日,中国信息通信研究院、中国交通运输协会信息专业委员会联合发起成立“交通运输业上云用云推进中心”,上海云轴信息科技有限公司(简称云轴科技ZStack)凭借优秀的产品技术创新能力和在交通运输领域的实践经验成为首批成员单位并…...

代码随想录算法训练营31期day4,力扣24+19+02.07+142

24,动指针 class Solution { public:ListNode* swapPairs(ListNode* head) {//建立虚拟头结点auto dummynew ListNode(-1);dummy->nexthead;for(auto pdummy;p->next&&p->next->next;){auto ap->next;auto ba->next;p->nextb;a->n…...

eNSP学习——利用单臂路由实现VLAN间路由

目录 原理概述 实验内容 实验目的 实验步骤 实验拓扑 实验编址 配置步骤 创建VLAN并配置Access、Trunk接口 配置路由器子接口和IP地址 配置路由器子接口封装VLAN 测试结果 原理概述 在以太网中,通常会使用VLAN技术隔离二层广播域来减少广播的影响&#…...

ISO27001认证:企业与个人发展的必备之选

ISO27001认证,对于企业和个人来说,都具有极高的价值和重要性。作为国际权威的信息安全管理体系标准,它为企业提供了保障信息安全、防范风险和提升竞争力的有力工具。 💼对企业的价值: ISO27001认证可以帮助企业满足国家…...

SpringBoot使用druid

SpringBoot使用druid 一、前言二、配置1、pom依赖2、配置文件yml3、配置类 一、前言 Java程序很大一部分要操作数据库,为了提高性能操作数据库的时候,又不得不使用数据库连接池。 Druid 是阿里巴巴开源平台上一个数据库连接池实现,结合了 C…...

TongWeb8交流常见问答集

问题1:今后用到你们TongWeb产品该联系谁? 答复: 1. 商务问题,如:报价、license授权、合同等请联系销售。 2. TongWeb技术问题,未签项目联系售前,已签项目联系售后。有指定项目经理的项目&…...

华为云AI开发平台ModelArts

华为云ModelArts:重塑AI开发流程的“智能引擎”与“创新加速器”! 在人工智能浪潮席卷全球的2025年,企业拥抱AI的意愿空前高涨,但技术门槛高、流程复杂、资源投入巨大的现实,却让许多创新构想止步于实验室。数据科学家…...

智慧医疗能源事业线深度画像分析(上)

引言 医疗行业作为现代社会的关键基础设施,其能源消耗与环境影响正日益受到关注。随着全球"双碳"目标的推进和可持续发展理念的深入,智慧医疗能源事业线应运而生,致力于通过创新技术与管理方案,重构医疗领域的能源使用模式。这一事业线融合了能源管理、可持续发…...

(十)学生端搭建

本次旨在将之前的已完成的部分功能进行拼装到学生端,同时完善学生端的构建。本次工作主要包括: 1.学生端整体界面布局 2.模拟考场与部分个人画像流程的串联 3.整体学生端逻辑 一、学生端 在主界面可以选择自己的用户角色 选择学生则进入学生登录界面…...

土地利用/土地覆盖遥感解译与基于CLUE模型未来变化情景预测;从基础到高级,涵盖ArcGIS数据处理、ENVI遥感解译与CLUE模型情景模拟等

🔍 土地利用/土地覆盖数据是生态、环境和气象等诸多领域模型的关键输入参数。通过遥感影像解译技术,可以精准获取历史或当前任何一个区域的土地利用/土地覆盖情况。这些数据不仅能够用于评估区域生态环境的变化趋势,还能有效评价重大生态工程…...

vue3+vite项目中使用.env文件环境变量方法

vue3vite项目中使用.env文件环境变量方法 .env文件作用命名规则常用的配置项示例使用方法注意事项在vite.config.js文件中读取环境变量方法 .env文件作用 .env 文件用于定义环境变量,这些变量可以在项目中通过 import.meta.env 进行访问。Vite 会自动加载这些环境变…...

深度学习习题2

1.如果增加神经网络的宽度,精确度会增加到一个特定阈值后,便开始降低。造成这一现象的可能原因是什么? A、即使增加卷积核的数量,只有少部分的核会被用作预测 B、当卷积核数量增加时,神经网络的预测能力会降低 C、当卷…...

华硕a豆14 Air香氛版,美学与科技的馨香融合

在快节奏的现代生活中,我们渴望一个能激发创想、愉悦感官的工作与生活伙伴,它不仅是冰冷的科技工具,更能触动我们内心深处的细腻情感。正是在这样的期许下,华硕a豆14 Air香氛版翩然而至,它以一种前所未有的方式&#x…...

推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材)

推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材) 这个项目能干嘛? 使用 gemini 2.0 的 api 和 google 其他的 api 来做衍生处理 简化和优化了文生图和图生图的行为(我的最主要) 并且有一些目标检测和切割(我用不到) 视频和 imagefx 因为没 a…...

08. C#入门系列【类的基本概念】:开启编程世界的奇妙冒险

C#入门系列【类的基本概念】:开启编程世界的奇妙冒险 嘿,各位编程小白探险家!欢迎来到 C# 的奇幻大陆!今天咱们要深入探索这片大陆上至关重要的 “建筑”—— 类!别害怕,跟着我,保准让你轻松搞…...

【网络安全】开源系统getshell漏洞挖掘

审计过程: 在入口文件admin/index.php中: 用户可以通过m,c,a等参数控制加载的文件和方法,在app/system/entrance.php中存在重点代码: 当M_TYPE system并且M_MODULE include时,会设置常量PATH_OWN_FILE为PATH_APP.M_T…...