spring boot 中我们应该知道的注解

本次我们主要对下面的注解进行了解:

1、基本bean 和 配置类型

@Configuration
@bean
@EnableConfigurationProperties
@ConfigurationProperties

conditional
@ConditionalOnClass
@ConditionalOnMissingBean
@ConditionalOnProperty
@ConditionalOnBean
@ConditionalOnExpression
@ConditionalOnMissingClass
@ConditionalOnNotWebApplication
@ConditionalOnResource


2、 解释开始

@Configuration : 被该注解注释的类会提供一个或则多个@bean修饰的方法并且会被spring容器处理来生成bean definitions。

@bean : 注解是必须修饰函数的,该函数可以提供一个bean。而且该函数的函数名必须和bean的名称一致,除了首字母不需要大写。

@EnableConfigurationProperties : 自动映射一个POJO到Spring Boot配置文件(默认是application.properties文件)的属性集。

@ConfigurationProperties : 是Spring Boot提供的方便属性注入的注解,功能其实和@Value类似


condition* 类型

@ConditionOnClass : 激活一个配置,当类路径中存在这个类时才会配置该类

@ConditionalOnMissingBean : 注解也是条件判断的注解,表示如果不存在对应的bean条件才成立 如果存在不再进行该bean的生成

@ConditionalOnProperty注解是条件判断的注解,表示如果配置文件中的响应配置项数值为true,才会对该bean进行初始化

@ConditionalOnBean : 在当前上下文中存在某个对象时,才会实例化一个Bean

@ConditionalOnExpression : 当表达式为true的时候,才会实例化一个Bean,表达式用${..}=false等来表示

@ConditionalOnMissingClass : 某个class类路径上不存在的时候,才会实例化一个Bean

@ConditionalOnNotWebApplication : 不是web应用时,才会执行

@ConditionalOnResource : 注解允许只有在特定资源出现时配置才会被包含。资源可以使用常见的Spring约定命名,例如file:/home/user/test.dat。

3、案例说明:

@ConditionalOnMissingBean
对于在@Configuretion @bean也是有加载顺序的, 对于下面的
先是@ConditionalOnMissingBean 执行发现里面的AuthenticationManager 不错在创建AuthenticationManager 这个bean会调到最下面的方法。调用完成后, 在调用自动usernamePasswordAuthenticationFilter(AuthenticationManager authenticationManager) 这个方法

@Bean
@ConditionalOnMissingBean(AuthenticationManager.class)
public UsernamePasswordAuthenticationFilter usernamePasswordAuthenticationFilter(AuthenticationManager authenticationManager)throws Exception{

    UsernamePasswordAuthenticationFilter usernamePasswordAuthenticationFilter = new UsernamePasswordAuthenticationFilter();
    usernamePasswordAuthenticationFilter.setAuthenticationManager(authenticationManager);
    usernamePasswordAuthenticationFilter.setAuthenticationDetailsSource(webAuthenticationDetailsSource);
    return usernamePasswordAuthenticationFilter;
}

@Bean
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
    return super.authenticationManagerBean();
}

当写成如下形式就, 也就是将bean 定义的顺序调换一下:

@Bean
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
    return super.authenticationManagerBean();
}

@Bean
@ConditionalOnMissingBean(AuthenticationManager.class)
public UsernamePasswordAuthenticationFilter usernamePasswordAuthenticationFilter(AuthenticationManager authenticationManager)throws Exception{

    UsernamePasswordAuthenticationFilter usernamePasswordAuthenticationFilter = new UsernamePasswordAuthenticationFilter();
    usernamePasswordAuthenticationFilter.setAuthenticationManager(authenticationManager);
    usernamePasswordAuthenticationFilter.setAuthenticationDetailsSource(webAuthenticationDetailsSource);
    return usernamePasswordAuthenticationFilter;
}

会执行 usernamePasswordAuthenticationFilter(AuthenticationManager authenticationManager)
因为AuthenticationManager bean 已经存在不会在执行其标注的相关代码块了。

@ConditionalOnBean
@ConditionalOnClass

  • 以上两个注解需要注意的是: 要写上相关参数(类, 类名, 类型等), 例如下面的

这里使用Eureka-client 里面的一个进行说明, 这个类就我随意找的

class OnRibbonAndEurekaEnabledCondition extends AllNestedConditions {

        public OnRibbonAndEurekaEnabledCondition() {
            super(ConfigurationPhase.REGISTER_BEAN);
        }

        @ConditionalOnClass(DiscoveryEnabledNIWSServerList.class)
        @ConditionalOnBean(SpringClientFactory.class)
        @ConditionalOnProperty(value = "ribbon.eureka.enabled", matchIfMissing = true)
        static class Defaults {}

        @ConditionalOnBean(EurekaClient.class)
        static class EurekaBeans {}

        @ConditionalOnProperty(value = "eureka.client.enabled", matchIfMissing = true)
        static class OnEurekaClientEnabled {}
    }

另外的一个: 通过字符形式的类名形式, 具体看看看注解里面都支持什么属性即可

@Configuration
@ConditionalOnClass(name = "javax.persistence.EntityManagerFactory")
@ConditionalOnBean(name = "entityManagerFactory")
static class JpaBatchConfiguration {

    @Bean
    public JpaBatchConfigurer batchConfigurer(BatchProperties properties, DataSource dataSource, ObjectProvider<TransactionManagerCustomizers> transactionManagerCustomizers,
            EntityManagerFactory entityManagerFactory) {
        return new JpaBatchConfigurer(properties, dataSource,
                transactionManagerCustomizers.getIfAvailable(), entityManagerFactory);
    }
}