SpringBoot——四大核心之自动装配(源码解析)

本文涉及的产品
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
全局流量管理 GTM,标准版 1个月
云解析 DNS,旗舰版 1个月
简介: SpringBoot——四大核心之自动装配(源码解析)

文章目录:


           1.开始

           2.pom文件

            3.聊聊spring-boot-start场景启动器

           4.言归正传——自动装配原理

           5.总结

1.开始


首先肯定要说一下SpringBoot的四大核心了:

·       自动装配:简单配置甚至零配置即可运行项目

·       起步依赖:场景启动器

·       Actuator:指标监控

·       命令行界面:命令行

这篇文章,我想和大家分享一下,我对自动装配这个核心的理解。

2.pom文件


从开始学框架到现在,一直都离不开一个东西,那就是Maven,之前没有学Maven的时候,项目中需要用到哪些东西,还要拷贝jar包,这就比较麻烦。而有了Maven之后,我们都知道它的核心是 pom.xml 文件,直接在这个文件中导入依赖就可以了,非常的方便。

下面,我们来看一下SpringBoot项目创建之后的pom文件。其中它主要是依赖一个父项目,主要是管理项目的资源过滤及插件!


点进去,发现它还有一个父依赖。再点到这个父依赖中,发现它没有父依赖了。

这里才是真正管理SpringBoot应用里面所有依赖版本的地方,SpringBoot的版本控制中心;

这也就是为什么我们导入依赖的时候不需要写版本号了,因为在这里SpringBoot已经对大量依赖的版本号做了统一管理,以后我们导入依赖默认是不需要写版本;但是如果导入的包没有在依赖中管理着就需要手动配置版本了。

3.聊聊spring-boot-start场景启动器


在我们创建一个SpringBoot项目之后,然后向其中的pom文件添加依赖的时候,我们会发现,添加的很多依赖都是以 spring-boot-start-XXX 这样的形式,我当时就按照字面意思去理解:springboot-开始-XXX的依赖。

那么,我们现在说的规范一点:spring-boot-start-XXX就是spring-boot的场景启动器。


spring-boot-starter-web:帮我们导入了web模块正常运行所依赖的组件;


spring-boot-starter-thymeleaf:帮我们导入了thymeleaf模板引擎正常运行所依赖的组件;


SpringBoot就是将所有的功能场景都抽取出来,做成一个个的starter(启动器),只需要在项目中引入这些starter即可,所有相关的依赖都会导入进来我们要用什么功能就导入什么样的场景启动器即可;我们未来也可以自己自定义 starter


说的形象一点,我们之前学SSM的时候,在pom文件中加入依赖,是不是有spring-contextspring-corespring-webmvc等等。而现在不需要了,你就可以直接写一个spring-boot-start-XXX完事了。之前SSM那种方式就是点了一份又一份的菜,而现在SpringBoot直接就是点了一个套餐,这个套餐中有很多你需要的菜名。

4.言归正传——自动装配原理


上面说了那么多,其实也是聊聊一个SpringBoot项目中常见的内容的一个理解吧。

下面我们就开始自动装配原理的分析了!!!

首先来看一下它的主启动类吧。在这个类上面,有一个 @SpringBootApplication 注解,那么它的作用就是说明这是一个Spring Boot的启动入口类,SpringBoot就应该运行这个类的 main 方法来启动 SpringBoot 应用。

我最初呢,就以为它不就是一个psvm,然后跑了一个run方法吗?但是但是一个简单的启动类并不简单!我们来分析一下这些注解都干了什么


我们点进去看看这个 @SpringBootApplication 注解。进入这个注解:可以看到上面还有很多其他注解!最上面的四个是Java中的元注解,就不说了,我们主要来看下面这三个注解。

·       @ComponentScan:这个注解在Spring中很重要,它对应XML配置中的元素(我们之前在xml文件中是不是写过一个标签<context:component-scan basepackage="XXX" />)。作用:自动扫描并加载符合条件的组件或者bean,将这个bean定义加载到IOC容器中。

·       @SpringBootConfiguration:作用:SpringBoot的配置类,标注在某个类上表示这是一个SpringBoot的配置类;我们点到这个注解中看看

我们发现这个注解的上面有一个@Configuration注解,这个注解不就是表示该类是一个配置类吗?在这个注解的上面还有一个@Component注解,表示启动类本身也是一个配置类,同时也是Spring中的一个组件而已,负责启动应用!

·       下面我们回到 @SpringBootApplication 这个注解中,上面已经说了两个,那么还剩一个 @EnableAutoConfiguration 这个注解,翻译一下好像是:开启自动配置功能注解。它是SpringBoot自动装配的一个核心了!!!以前我们需要自己配置的东西,而现在SpringBoot可以自动帮我们配置@EnableAutoConfiguration这个注解就是告诉SpringBoot开启自动配置功能,这样自动配置才能生效。

那我们点到 @EnableAutoConfiguration 这个注解中,看看吧


四个元注解不说了,我们发现除此之外还有两个注解。

·       @AutoConfigurationPackage :自动配置包,点进去看看,它的上面有一个@Import注解。


首先说一下:我这个项目主启动类的包路径是 com.songzihao.springboot

Spring底层注解@Import 给容器中导入一个组件。(利用Registrar给容器中导入一系列组件,那么它是将指定的一个包下的所有组件导入进来吗?当然不是,Debug执行我们可以看到,所导入的组件都位于主启动类所在包及其子包下)

Registrar.class 作用:将主启动类的所在包及包下面所有子包里面的所有组件扫描到Spring容器;这也就是为什么SpringBoot项目创建之后新建的其他包需要方便主启动类所在包的子包中了。因为这有这样才会被扫描并加载到Spring容器中。

好了,这个@AutoConfigurationPackage注解分析完了,我们回到@EnableAutoConfiguration这个注解中,它上面还有一个 @Import({AutoConfigurationImportSelector.class}) 这个注解,翻译一下:自动配置导入选择器,那么它会导入哪些组件的选择器呢?我们点击去这个类看源码

发现这是一个类,我们主要来看源码中的这几个方法:👇👇👇


点进去这个方法,我们可以看到,在这个方法的源码中,频繁的在对 configurations 对象做一系列操作,所以我们就不得不重视起来这个configurations 对象,

它是通过调用 getCandidateConfigurations 这个方法得到的。


我们在这里打个断点看看调用完这个方法会得到什么,可以看到这里加载了大量的自动配置组件。


1.    首先利用getAutoConfigurationEntry(annotationMetadata);给容器中批量导入一些组件

2.    调用List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes)获取到所有需要导入到容器中的配置类

3.    利用工厂加载 Map<String, List<String>> loadSpringFactories(@Nullable ClassLoader classLoader);得到所有的组件

4.    META-INF/spring.factories位置来加载一个文件。默认扫描我们当前系统里面所有META-INF/spring.factories位置的文件。


关于第三步和第四步请继续往下看:👇👇👇


这个方法呢,首先是调用了SpringFactoriesLoader.loadFactoryNames方法,我们点进去看看这里面有什么。


如果仔细看源码了话,你会发现经常看到一个东西就是:META-INF/spring.factories,那么它里面到底有什么呢?答案在这里:👇👇👇 


在这里面我们看到了很多自动配置的文件;这就是自动配置根源所在!

我们可以找点熟悉的看看,比如:RedisAutoConfiguration,它的上面有一些@Conditional相关的注解。


可以看到这些一个个的都是JavaConfig配置类,而且都注入了一些Bean,可以找一些自己认识的类,看着熟悉一下! 

5.总结


1.    SpringBoot启动时会加载大量的自动配置类 xxxAutoConfiguration

2.    每个自动配置类按照条件进行生效,一旦这个自动配置类生效,那么这个它就会向容器中添加各种@Bean指定好的组件(只要我们要用到的组件在自动配置类中有,那么我们就不需要再进行配置了)。

3.    所有在配置文件中能配置的属性值都是在xxxProperties属性类中封装好了,这些值从xxxProperties属性类里面拿。这些类里面的每一个属性又是和配置文件绑定好的,我们就可以在配置文件中指定这些属性的值。

4.    定制化配置:用户可以直接通过定义@Bean替换底层的组件。


·       xxxAutoConfiguration:自动配置类给容器中添加组件。

·       xxxProperties:封装配置文件中可以定义的相关属性。

·       xxxAutoConfiguration ---> 组件 ---> xxxProperties里面拿值----> application.properties


不知道大家有没有发现,很多需要待加载的类都放在类路径下的META-INF/Spring.factories文件下,而不是直接写死这代码,这样做就可以很方便我们自己或者是第三方去扩展,我们也可以实现自己starter,让SpringBoot去加载。现在明白为什么 SpringBoot 可以实现零配置,开箱即用了吧!

相关文章
|
5天前
|
监控 Java 应用服务中间件
高级java面试---spring.factories文件的解析源码API机制
【11月更文挑战第20天】Spring Boot是一个用于快速构建基于Spring框架的应用程序的开源框架。它通过自动配置、起步依赖和内嵌服务器等特性,极大地简化了Spring应用的开发和部署过程。本文将深入探讨Spring Boot的背景历史、业务场景、功能点以及底层原理,并通过Java代码手写模拟Spring Boot的启动过程,特别是spring.factories文件的解析源码API机制。
18 2
|
21天前
|
数据采集 监控 前端开发
二级公立医院绩效考核系统源码,B/S架构,前后端分别基于Spring Boot和Avue框架
医院绩效管理系统通过与HIS系统的无缝对接,实现数据网络化采集、评价结果透明化管理及奖金分配自动化生成。系统涵盖科室和个人绩效考核、医疗质量考核、数据采集、绩效工资核算、收支核算、工作量统计、单项奖惩等功能,提升绩效评估的全面性、准确性和公正性。技术栈采用B/S架构,前后端分别基于Spring Boot和Avue框架。
|
6天前
|
存储 安全 Linux
Golang的GMP调度模型与源码解析
【11月更文挑战第11天】GMP 调度模型是 Go 语言运行时系统的核心部分,用于高效管理和调度大量协程(goroutine)。它通过少量的操作系统线程(M)和逻辑处理器(P)来调度大量的轻量级协程(G),从而实现高性能的并发处理。GMP 模型通过本地队列和全局队列来减少锁竞争,提高调度效率。在 Go 源码中,`runtime.h` 文件定义了关键数据结构,`schedule()` 和 `findrunnable()` 函数实现了核心调度逻辑。通过深入研究 GMP 模型,可以更好地理解 Go 语言的并发机制。
|
18天前
|
消息中间件 缓存 安全
Future与FutureTask源码解析,接口阻塞问题及解决方案
【11月更文挑战第5天】在Java开发中,多线程编程是提高系统并发性能和资源利用率的重要手段。然而,多线程编程也带来了诸如线程安全、死锁、接口阻塞等一系列复杂问题。本文将深度剖析多线程优化技巧、Future与FutureTask的源码、接口阻塞问题及解决方案,并通过具体业务场景和Java代码示例进行实战演示。
38 3
|
20天前
|
JavaScript Java 项目管理
Java毕设学习 基于SpringBoot + Vue 的医院管理系统 持续给大家寻找Java毕设学习项目(附源码)
基于SpringBoot + Vue的医院管理系统,涵盖医院、患者、挂号、药物、检查、病床、排班管理和数据分析等功能。开发工具为IDEA和HBuilder X,环境需配置jdk8、Node.js14、MySQL8。文末提供源码下载链接。
|
1月前
|
存储
让星星⭐月亮告诉你,HashMap的put方法源码解析及其中两种会触发扩容的场景(足够详尽,有问题欢迎指正~)
`HashMap`的`put`方法通过调用`putVal`实现,主要涉及两个场景下的扩容操作:1. 初始化时,链表数组的初始容量设为16,阈值设为12;2. 当存储的元素个数超过阈值时,链表数组的容量和阈值均翻倍。`putVal`方法处理键值对的插入,包括链表和红黑树的转换,确保高效的数据存取。
53 5
|
1月前
|
JavaScript 安全 Java
如何使用 Spring Boot 和 Ant Design Pro Vue 实现动态路由和菜单功能,快速搭建前后端分离的应用框架
本文介绍了如何使用 Spring Boot 和 Ant Design Pro Vue 实现动态路由和菜单功能,快速搭建前后端分离的应用框架。首先,确保开发环境已安装必要的工具,然后创建并配置 Spring Boot 项目,包括添加依赖和配置 Spring Security。接着,创建后端 API 和前端项目,配置动态路由和菜单。最后,运行项目并分享实践心得,包括版本兼容性、安全性、性能调优等方面。
145 1
|
20天前
|
JavaScript 安全 Java
如何使用 Spring Boot 和 Ant Design Pro Vue 构建一个具有动态路由和菜单功能的前后端分离应用。
本文介绍了如何使用 Spring Boot 和 Ant Design Pro Vue 构建一个具有动态路由和菜单功能的前后端分离应用。首先,创建并配置 Spring Boot 项目,实现后端 API;然后,使用 Ant Design Pro Vue 创建前端项目,配置动态路由和菜单。通过具体案例,展示了如何快速搭建高效、易维护的项目框架。
95 62
|
18天前
|
JavaScript 安全 Java
如何使用 Spring Boot 和 Ant Design Pro Vue 构建一个前后端分离的应用框架,实现动态路由和菜单功能
本文介绍了如何使用 Spring Boot 和 Ant Design Pro Vue 构建一个前后端分离的应用框架,实现动态路由和菜单功能。首先,确保开发环境已安装必要的工具,然后创建并配置 Spring Boot 项目,包括添加依赖和配置 Spring Security。接着,创建后端 API 和前端项目,配置动态路由和菜单。最后,运行项目并分享实践心得,帮助开发者提高开发效率和应用的可维护性。
35 2
|
2月前
|
前端开发 JavaScript Java
基于Java+Springboot+Vue开发的大学竞赛报名管理系统
基于Java+Springboot+Vue开发的大学竞赛报名管理系统(前后端分离),这是一项为大学生课程设计作业而开发的项目。该系统旨在帮助大学生学习并掌握Java编程技能,同时锻炼他们的项目设计与开发能力。通过学习基于Java的大学竞赛报名管理系统项目,大学生可以在实践中学习和提升自己的能力,为以后的职业发展打下坚实基础。
219 3
基于Java+Springboot+Vue开发的大学竞赛报名管理系统

推荐镜像

更多