早上大鸟刚到公司,然后就看到小菜已经早早做到了工位上了,小菜看到大鸟后,立刻来兴趣了,“大神,继续解决我的问题吧,你看我昨天思考它睡觉都没有睡好,我昨天也查了一下,但是还是想跟你磨擦一下,嘿嘿,外一有新火花呢!”大鸟看看小菜这么好学,而且看上班时间还在, 开启了讲故事模式。
大鸟打开电脑,“来,咱们一起看源码!介绍一下这些注解,首先解答第一个问题:为什么Controller没有加包扫描,然后也可以被扫描到。”
1.首先是引导配置类@SpringBootApplication
“ctrl+鼠标左键”,进入到SpringBoot引导类@SpringBootApplication中,然后可以看到源码
包括下面注解;
可以看到注解@ComponentScan,它的作用就是这个启动类所在的包以及所在包下的子包都会被扫描,所以也就是昨天的第一个问题“”。
大鸟看小菜听的津津有味,然后说再给你扩展一下其他的几个注解 吧。
2.@SpringBootConfiguration
既标注该类是Spring的一个配置类
3.@EnableAutoConfiguration
即SpringBoot自动配置功能开启。
(1)按住Ctrl点击查看注解@EnableAutoConfiguration
(2)其中,@Import(AutoConfigurationImportSelector.class) 导入了AutoConfigurationImportSelector类。按住Ctrl点击查看AutoConfigurationImportSelector源码
(3)其中,SpringFactoriesLoader.loadFactoryNames 方法的作用就是从META-INF/spring.factories文件中读取指定类对应的类名称列表。
spring.factories 文件中有关自动配置的配置信息如下:
上面配置文件存在大量的以Configuration为结尾的类名称,这些类就是存有自动配置信息的类,而SpringApplication在获取这些类名后再加载。
(4)我们以ServletWebServerFactoryAutoConfiguration为例来分析源码:下面的@EnableConfigurationProperties(ServerProperties.class) 代表加载ServerProperties服务器配置属性类。
&mesp;(5)进入ServerProperties.class源码如下:
其中prefix = “server” 表示SpringBoot配置文件中的前缀,SpringBoot会将配置文件中以server开始的属性映射到该类的字段中。映射关系如下:
小菜恍然大悟,顿时觉醒了,突然发现好东西都在源码上呢,然后说“大神,第一个问题我彻底明白了,咱们继续第二个问题吧–-SpringBoot可以减少jar包重突嘛,如何体现的呀!”
大鸟说,“好,咱们从起步依赖原理开始分析,也就是分享两个依赖包----spring-boot-starter-parent、spring-boot-starter-web”。
首先剖析spring-boot-starter-parent。
1.按住Ctrl点击pom.xml中的spring-boot-starter-parent,跳转到了spring-boot-starter-parent的pom.xml,xml配置如下。
2.按住Ctrl点击pom.xml中的spring-boot-starter-dependencies,跳转到了spring-boot-starter-dependencies的pom.xml,xml配置如下:
大鸟调整了一下眼镜,说"公上面的这些版本号,你看出了什么嘛?"。小菜也是个爱观察的孩子,瞅了瞅,然后说“从上面的spring-boot-starter-dependencies的pom.xml中我们可以发现,一部分坐标的版本、依赖管理、插件管理已经定义好,所以我们的SpringBoot工程继承spring-boot-starter-parent后已经具备版本锁定等配置了。所以起步依赖的作用就是进行依赖的传递。”大鸟很满意的点了点头,说,“”我们再看spring-boot-starter-web“”。
1,。按住Ctrl点击pom.xml中的spring-boot-starter-web,跳转到了spring-boot-starter-web的pom.xml,xml配置如下:
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<version>2.0.1.RELEASE</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-json</artifactId>
<version>2.0.1.RELEASE</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<version>2.0.1.RELEASE</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.hibernate.validator</groupId>
<artifactId>hibernate-validator</artifactId>
<version>6.0.9.Final</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>5.0.5.RELEASE</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.0.5.RELEASE</version>
<scope>compile</scope>
</dependency>
</dependencies>
大鸟说“你看,从上面的spring-boot-starter-web的pom.xml中我们可以发现,spring-boot-starter-web就是将web开发要使用的spring-web、spring-webmvc等坐标进行了“打包”,这样我们的工程只要引入spring-boot-starter-web起步依赖的坐标就可以进行web开发了,同样体现了依赖传递的作用。”
&emspl;下面来看第三个问题“SpringBoot加载配置文件,是如何加载的呢?”
- 按住Ctrl点击pom.xml中的spring-boot-starter-parent,跳转到了spring-boot-starter-parent的pom.xml,xml配置如下。
大鸟说“通过上面的配置文件,可以看出SpringBoot是加载resources下面的"yml、yaml、properties文件",但是有先后顺序的加载。然后昨天的问题解决完了呢,然后对于yml文件也是有格式介绍的,这个需要你自己去注意咯!”
小菜非常激动的说,“好的,好的,你太牛了!”这时候陆陆续续的也有不少人来公司了,一切归于了瓶颈,大鸟和小菜分别到自己的工位上,开始一天的码代码工作了。