Java

SpringBoot初体验

2020-03-06  本文已影响0人  愤怒的老照

学习Springboot之前,肯定要有javaweb、Spring的基础,在没有接触Springboot的时候,并不能体会Springboot的简便,但是Springboot确实很火,就花了时间学习了一下,发现开箱即用,几乎不需要配置。既然SpringBoot的核心是Spring,为什么Spring的配置都不需要了呢?跟着百度,糊里糊涂的了解了一下,只是了解了一下思路...

疑惑一:自动配置

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan(
    excludeFilters = {@Filter(
    type = FilterType.CUSTOM,
    classes = {TypeExcludeFilter.class}
), @Filter(
    type = FilterType.CUSTOM,
    classes = {AutoConfigurationExcludeFilter.class}
)}
)
public @interface SpringBootApplication {}
  1. @ComponentScan:这个注解是组件扫描这个是我们最熟悉的注解,即使没有使用过注解也经常在spring的配置文件中使用过<context:component-scan base-package="com.xxx.xxx"/>, 组件扫描就是扫描指定的包下的类,并加载符合条件的组件。
  2. @SpringBootConfiguration:其实就是一个@Configuration,表明这是一个配置类
  3. @EnableAutoConfiguration:这是自动配置最重要的一个注解了,开启自动配置功能,以前需要自动配置的东西,Spring Boot帮我们自动配置
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@AutoConfigurationPackage
@Import({AutoConfigurationImportSelector.class})
public @interface EnableAutoConfiguration {
    String ENABLED_OVERRIDE_PROPERTY = "spring.boot.enableautoconfiguration";

    Class<?>[] exclude() default {};

    String[] excludeName() default {};
}

@AutoConfigurationPackage:将主配置类所在的包下的所有组件,添加到Spring容器中

@Import:给容器导入AutoConfigurationImportSelector组件,其中有一个selectImports方法 1.png 跟着代码走进来,发现资源是从类路径下的META-INF/spring.factories获取EnableAutoConfiguration指定的值,点开自动配置依赖的spring.factories: 2.png

,这也就是为什么不需要我们配置的原因了,Springboot帮我们配置好了

疑惑二:自动配置条件

参考DataSourceConfiguration,
数据源有三个配置,不可能将三个都加载到容器中,这时候@Conditional条件判断就起作用了:

@Configuration(proxyBeanMethods = false)
// tomcat自带的datasource连接池,由于默认情况下spring-boot未引入org.apache.tomcat.jdbc.pool.DataSource对应的依赖包,
       // 根据@ConditionalOnClass注解的作用,这个配置不会生效
    @ConditionalOnClass(org.apache.tomcat.jdbc.pool.DataSource.class)
    @ConditionalOnMissingBean(DataSource.class)
    @ConditionalOnProperty(name = "spring.datasource.type", havingValue = "org.apache.tomcat.jdbc.pool.DataSource",
            matchIfMissing = true)
    static class Tomcat {}
        // 这是SpringBoot默认的数据源
    /**
     * Hikari DataSource configuration.
     */
    @Configuration(proxyBeanMethods = false)
        // 存在这个class,继续执行
    @ConditionalOnClass(HikariDataSource.class)
    // 如果不存在数据源bean,才继续执行,如果我们添加Druid数据源,此处就不在继续执行
    @ConditionalOnMissingBean(DataSource.class)
        // 配置文件中存在spring.datasource.type,且为com.zaxxer.hikari.HikariDataSource,或者不存在这个属性的时候,继续执行
    @ConditionalOnProperty(name = "spring.datasource.type", havingValue = "com.zaxxer.hikari.HikariDataSource",
            matchIfMissing = true)
    static class Hikari {}

    /**
     * DBCP DataSource configuration.
     */
    @Configuration(proxyBeanMethods = false)
    @ConditionalOnClass(org.apache.commons.dbcp2.BasicDataSource.class)
        // 上一步已经加载了DataSource,这一步不再执行
    @ConditionalOnMissingBean(DataSource.class)
    @ConditionalOnProperty(name = "spring.datasource.type", havingValue = "org.apache.commons.dbcp2.BasicDataSource",
            matchIfMissing = true)
    static class Dbcp2 {}

    /**
     * Generic DataSource configuration.
     */
    // 如果配置了Druid或其他数据源,会创建默认的Bean,否则跳过
    @Configuration(proxyBeanMethods = false)
    @ConditionalOnMissingBean(DataSource.class)
    @ConditionalOnProperty(name = "spring.datasource.type")
    static class Generic {

        @Bean
        DataSource dataSource(DataSourceProperties properties) {
            return properties.initializeDataSourceBuilder().build();
        }

    }


从上面的代码可以知道spring-boot默认实现了hikari连接池,我们如果想更换为Druid连接池,只需要引入相应的连接池,并spring.datasource.type配置为Druid的类,所以Springboot会根据各种条件,来确保只有一项可以生效。

参考自:
https://blog.csdn.net/song_java/article/details/86509971
https://github.com/lxy-go/SpringBoot

上一篇下一篇

猜你喜欢

热点阅读