【SpringBoot】Spring Boot自动配置概览

目录

  • 背景
  • 自动装配/自动配置
  • springboot是如何实现自动配置的
    • 核心注解
    • AutoConfigurationImportSelector 类的继承体系
      • Spring Boot 提供的条件注解
      • 示例
      • 注意版本

背景

  • 没有 Spring Boot 的情况下,我们引入第三方依赖之后,需要手动配置。

  • 比如需要手动将引入的第三方依赖通过 xml 配置或注解的方式注入到 Ioc 容器中,并可能需要对注入到Ioc容器中的bean进行一些配置,非常麻烦。

  • 但是,在Spring Boot 中,我们直接引入一个 starter 即可。例如:

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-redis</artifactId>
    </dependency>
    

自动装配/自动配置

  • SpringBoot2.7以前定义了一套接口规范,这套规范规定:
    • SpringBoot 在启动时会扫描外部引用 jar 包中的 META-INF/spring.factories 文件,将文件中配置的类型信息加载到 Spring 容器(此处涉及到 JVM 类加载机制与 Spring 的容器知识),并执行类中定义的各种操作。
    • 对于外部 jar 来说,只需要按照 SpringBoot 定义的标准,就能将自己的功能装置进 SpringBoot
  • 引入 starter 之后,我们通过少量注解和一些简单的配置就能使用第三方组件提供的功能了
  • 所以说,其实自动装配可以简单的理解为:通过注解或者一些简单的配置就能在spring boot的帮助下实现某款功能

springboot是如何实现自动配置的

核心注解

首先我们先来看一些 SpringBoot 项目的核心注解 @SpringBootApplication:
在这里插入图片描述

  • 点击 @SpringBootConfiguration 注解,发现这个注解其实就是一个配置注解,SpringBoot 把 @Configuration 注解做一个包装。

  • 所以说 @SpringBootApplication 是一个复合注解,大概就可以把 @SpringBootApplication 看作是这三个注解的集合:

    • @EnableAutoConfiguration:启用 SpringBoot 的自动配置机制。
    • @Configuration:允许在上下文中注册额外的 bean 或导入其他配置类,作用与applicationContext.xml 的功能相同。
    • @ComponentScan: 扫描包下的类中添加了@Component (@Service,@Controller,@Repostory,@RestController)注解的类 ,并添加的到spring的容器中,可以自定义不扫描某些 bean。如下图所示,容器中将排除TypeExcludeFilter和AutoConfigurationExcludeFilter。
      在这里插入图片描述
  • 也就是说,@EnableAutoConfiguration 是实现自动装配的核心注解,@EnableAutoConfiguratio的内部如下所示。
    在这里插入图片描述

  • 思考:AutoConfigurationImportSelector 类到底做了什么?

AutoConfigurationImportSelector 类的继承体系

在这里插入图片描述在这里插入图片描述在这里插入图片描述

  • 可以看出:AutoConfigurationImportSelector 类实现了 ImportSelector 接口,也就实现了这个接口中的 selectImports 方法

  • 该方法主要用于获取所有符合条件的类的全限定类名,需要为这些类创建对象并加载到 IoC 容器中
    在这里插入图片描述

  • 这里我们需要重点关注一下 getAutoConfigurationEntry方法,这个方法主要负责加载自动配置类的。该方法调用链如下:
    在这里插入图片描述

    protected AutoConfigurationEntry getAutoConfigurationEntry(AnnotationMetadata annotationMetadata) {
        //第1步:判断自动装配开关是否打开
       if (!isEnabled(annotationMetadata)) {
          return EMPTY_ENTRY;
       }
        //第2步:用于获取注解中的exclude和excludeName。
        //获取注解属性
       AnnotationAttributes attributes = getAttributes(annotationMetadata); 
        //第3步:获取需要自动装配的所有配置类,读取META-INF/spring.factories
        //读取所有预配置类
       List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes);
        //第4步:符合条件加载
        //去掉重复的配置类
       configurations = removeDuplicates(configurations);
        //执行
       Set<String> exclusions = getExclusions(annotationMetadata, attributes);
        //校验
       checkExcludedClasses(configurations, exclusions);
        //删除
       configurations.removeAll(exclusions);
        //过滤
       configurations = getConfigurationClassFilter().filter(configurations);
       fireAutoConfigurationImportEvents(configurations, exclusions);
        //创建自动配置的对象
       return new AutoConfigurationEntry(configurations, exclusions);
    }
    
    • 第1步:判断自动装配开关是否打开。默认 spring.boot.enableautoconfiguration = true,可在 application.properties 或 application.yml 中设置。
    • 第2步:用于获取 EnableAutoConfiguration 注解中的 exclude 和 excludeName。
    • 第3步:从 META-INF/spring.factories 读取需要自动装配的所有配置类。所有 Spring Boot Starter 下的 META-INF/spring.factories 都会被读取到。
    • 第4步:spring.factories 中这么多配置,每次启动都要全部加载么?很明显,这是不现实的。我们 debug 到后面你会发现,configurations 的值变小了。。因为,这一步有经历了一遍筛选过滤,@ConditionOnXXX 中的所有条件都满足,该类才会生效。
      在这里插入图片描述

Spring Boot 提供的条件注解

  1. @ConditionalOnBean:当容器里有指定 Bean 的条件下
  2. @ConditionalOnMissingBean:当容器里没有指定 Bean 的情况下
  3. @ConditionalOnSingleCandidate:当指定 Bean 在容器中只有一个,或者虽然有多个但是指定首选 Bean
  4. @ConditionalOnClass:当类路径下有指定类的条件下
  5. @ConditionalOnMissingClass:当类路径下没有指定类的条件下
  6. @ConditionalOnProperty:指定的属性是否有指定的值
  7. @ConditionalOnResource:类路径是否有指定的值
  8. @ConditionalOnExpression:基于 SpEL 表达式作为判断条件
  9. @ConditionalOnJava:基于 Java 版本作为判断条件
  10. @ConditionalOnJndi:在 JNDI 存在的条件下差在指定的位置
  11. @ConditionalOnNotWebApplication:当前项目不是 Web 项目的条件下
  12. @ConditionalOnWebApplication:当前项目是 Web 项 目的条件下

示例

以redis为例,然后在当前springboot项目中双击Shift,在弹出的页面中搜索找到RedisAutoConfiguration类。

  • 由RedisAutoConfiguration类上面的注解可知,RedisAutoConfiguration类有一个bean加载控制的注解。也就是说,当前类要想加载成bean,必须在当前项目中导入RedisOperations这个类,也就是当前类加载成bean的触发条件,而RedisOperations这个类在我们导入的redis的依赖包中。
  • 在RedisAutoConfiguration类上方有一个 @EableConfigurationProperties 注解。进入@EableConfigurationProperties 注解里的RedisProperties类中,如下图所示, RedisProperties 类上方有一个 @ConfigurationProperties 注解,此注解用来将配置文件中前缀为 spring.redis 的配置值绑定到类中属性上。
  • 但是可以发现,RedisProperties类里很多属性已经配置了默认值。也就是说,如果 springboot 配置文件中没有配置值,则 springboot 会采用 RedisProperties 类中属性的默认值来作为redis这项技术的默认配置值。
    在这里插入图片描述

注意版本

spring.factories 功能在 SpringBoot 2.7 已经废弃,并且在 SpringBoot 3.0 移除。但机制还是类似的

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

基于Android Studio 制作仿微信APP界面完成在线聊天发布朋友圈等功能

&#x1f345;文章末尾有获取完整项目源码方式&#x1f345; 目录 一、引言 二、视频效果 三、前期准备 四、详细设计与实现 1.启动页 2.登陆注册页 3.登录页 4.注册页 5.首页 6.聊天页面 7.通讯录页面 8.发现页面 9.我的页面 10. 个人信息页面 11.修改昵…

Spring Boot | Spring Security ( SpringBoot安全管理 )、Spring Security中 的 “自定义用户认证“

目录 : Spring Boot 安全管理 &#xff1a;一、Spring Security 介绍二、Spring Security 快速入门2.1 基础环境搭建 :① 创建Spring Boot 项目② 创建 html资源文件③ 编写Web控制层 2.2 开启安全管理效果测试 :④ 添加 spring-boot-starter-security 启动器⑤ 项目启动测试 三…

Dockerfile部署LNMP

目录 一、项目模拟 1. 项目环境 2. 服务器环境 3. 任务需求 二、Linux系统基础镜像 三、Nginx 1. 建立工作目录 2. 编写Dockerfile脚本 3. 准备nginx.conf配置文件 4. 生成镜像 5. 创建自定义网络 6. 启动镜像容器 7. 验证nginx 四、Mysql 1. 建立工作目录 2. …

# 使用 spring boot 时,@Autowired 注解 自动装配注入时,变量报红解决方法:

使用 spring boot 时&#xff0c;Autowired 注解 自动装配注入时&#xff0c;变量报红解决方法&#xff1a; 1、使用 Resource 代替 Autowired 注解&#xff0c;根据类型注入改为根据名称注入&#xff08;建议&#xff09;。 2、在 XXXMapper 上添加 Repository 注解&#xff0…

(2024,一致性模型,强化学习,MDP,DDPO)一致性模型的强化学习:更快的奖励引导文本到图像生成

RL for Consistency Models: Faster Reward Guided Text-to-Image Generation 公和众和号&#xff1a;EDPJ&#xff08;进 Q 交流群&#xff1a;922230617 或加 VX&#xff1a;CV_EDPJ 进 V 交流群&#xff09; 部分图像上传缓慢&#xff0c;可看原论文或在 EDPJ 查看 目录 …

2024/4/29 英语每日一段

Many have turned to cheaper, hand-rolled tobacco instead of normal cigarettes, with young women telling The Times that the habit was a social way to get rid of “anxious energy”. The news comes as the government voted on Tuesday to phase out smoking in Br…

RCE复习(ctfhub下)

先了解一下命令注入的知识点&#xff1a; 知识点 1、常见的拼接符 A ; B 先执行A&#xff0c;再执行BA & B 简单的拼接A | B 显示B的执行结果A&&B A执行成功之后才会执行BA || B A执行失败之后才会执行B , 在特殊情况下可代替空格…

pytorch 实现语义分割 PSPNet

语意分割是指一张图片上包含多个物体&#xff0c;通过语义分割可以识别物体分类、物体名称、像素识别的任务。和物体检测不同&#xff0c;他不会将物体框出来&#xff0c;而是根据像素的归属把物体标注出来。PSPNet 的输入是一张图片&#xff0c;例如300500&#xff0c;那么输出…

Redis基本數據結構 ― List

Redis基本數據結構 ― List 介紹常用命令範例1. 將元素推入List中2. 取得List內容3. 彈出元素 介紹 Redis中的List結構是一個雙向鏈表。 LPUSH LPOP StackLPUSH RPOP QueueLPUSH BRPOP Queue(消息隊列) 常用命令 命令功能LPUSH將元素推入列表左端RPUSH將元素推入列表右…

特别推荐一个学习开发编程的网站

http://www.somecore.cn/ 为开发人员提供一系列好看的技术备忘单&#xff0c;方便开发过程中速查基本语法、快捷键、命令&#xff0c;节省查找时间&#xff0c;提高开发效率。 【人生苦短&#xff0c;抓住重点】

Java 面向对象—重载和重写/覆盖(面试)

重载和重写/覆盖&#xff1a; 重载&#xff08;overload&#xff09;&#xff1a; Java重载是发生在本类中的&#xff0c;允许同一个类中&#xff0c;有多个同名方法存在&#xff0c;方法名可以相同&#xff0c;方法参数的个数和类型不同&#xff0c;即要求形参列表不一致。重载…

有趣的 CSS 图标整合技术!sprites精灵图,css贴图定位

你好&#xff0c;我是云桃桃。 一个希望帮助更多朋友快速入门 WEB 前端的程序媛。 云桃桃-大专生&#xff0c;一枚程序媛&#xff0c;感谢关注。回复 “前端基础题”&#xff0c;可免费获得前端基础 100 题汇总&#xff0c;回复 “前端工具”&#xff0c;可获取 Web 开发工具合…

【C语言进阶】程序编译中的预处理操作

&#x1f4da;作者简介&#xff1a;爱编程的小马&#xff0c;正在学习C/C&#xff0c;Linux及MySQL.. &#x1f4da;以后会将数据结构收录为一个系列&#xff0c;敬请期待 ● 本期内容讲解C语言中程序预处理要做的事情 目录 1.1 预处理符号 1.2 #define 1.2.1 #define定义标识…

数据结构(01)——链表OJ

目录 移除链表元素 思路1 不创建虚拟头节点 思路2 创建虚拟头节点 反转链表 寻找链表中间节点 判断链表是否相交 回文链表 环形链表 环形链表|| 移除链表元素 . - 力扣&#xff08;LeetCode&#xff09; 要想移除链表的元素&#xff0c;那么只需要将目标节点的前一…

07_for循环返回值while循环

文章目录 1.循环返回值2.yield接收for返回值3.scala调用yield方法创建线程对象4.scala中的while循环5.scala中的流程控制 1.循环返回值 for循环返回值是Unit 原因是防止产生歧义&#xff1b; 2.yield接收for返回值 // 2.yield关键字打破循环&#xff0c;可以使for循环输出…

智慧农业设备——虫情监测系统

随着科技的不断进步和农业生产的日益现代化&#xff0c;智慧农业成为了新时代农业发展的重要方向。其中&#xff0c;虫情监测系统作为智慧农业的重要组成部分&#xff0c;正逐渐受到广大农户和农业专家的关注。 虫情监测系统是一种基于现代传感技术、图像识别技术和大数据分析技…

面试笔记——线程池

线程池的核心参数&#xff08;原理&#xff09; public ThreadPoolExecutor(int corePoolSize,int maximumPoolSize,long keepAliveTime,TimeUnit unit,BlockingQueue<Runnable> workQueue,ThreadFactory threadFactory,RejectedExecutionHandler handler)corePoolSize …

25计算机考研院校数据分析 | 四川大学

四川大学(Sichuan University)简称“川大”&#xff0c;由中华人民共和国教育部直属&#xff0c;中央直管副部级建制&#xff0c;是世界一流大学建设高校、985工程”、"211工程"重点建设的高水平综合性全国重点大学&#xff0c;入选”2011计划"、"珠峰计划…

PostgreSQL的学习心得和知识总结(一百四十)|深入理解PostgreSQL数据库 psql工具 \set 变量内部及HOOK机制

目录结构 注&#xff1a;提前言明 本文借鉴了以下博主、书籍或网站的内容&#xff0c;其列表如下&#xff1a; 1、参考书籍&#xff1a;《PostgreSQL数据库内核分析》 2、参考书籍&#xff1a;《数据库事务处理的艺术&#xff1a;事务管理与并发控制》 3、PostgreSQL数据库仓库…

【能力展现】魔改ZXING源码实现商业级DM码检测能力

学习《OpenCV应用开发&#xff1a;入门、进阶与工程化实践》一书 做真正的OpenCV开发者&#xff0c;从入门到入职&#xff0c;一步到位&#xff01; 什么是DM码 dataMatrix是一种二维码&#xff0c;原名datacode&#xff0c;由美国国际资料公司于1989年发明。dataMatrix二维码…