@Conditional 注解

阅读 1

20小时前

 什么是 @Conditional

@Conditional 是 Spring 4.0 引入的核心注解,用于根据特定条件决定是否创建某个 Bean 或导入某个配置类

它位于 Spring 框架的 org.springframework.context.annotation 包中,是实现条件化装配(Conditional Bean Registration) 的基石。

内置条件注解实战(开箱即用)

Spring 提供了多个基于 @Conditional 的便捷注解,直接使用即可:

1. @ConditionalOnProperty:基于配置属性

@Configuration
public class EmailConfig {

    @Bean
    @ConditionalOnProperty(
        name = "email.enabled", 
        havingValue = "true", 
        matchIfMissing = false
    )
    public EmailService emailService() {
        return new SmtpEmailService();
    }
}

✅ 只有当 application.ymlemail.enabled=true 时,才创建 EmailService

2. @ConditionalOnClass:基于类路径存在性

@Configuration
@ConditionalOnClass(RedisTemplate.class)
public class RedisConfig {

    @Bean
    public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) {
        RedisTemplate<String, Object> template = new RedisTemplate<>();
        template.setConnectionFactory(factory);
        return template;
    }
}

✅ 只有当类路径下存在 RedisTemplate 类时(即引入了 spring-boot-starter-data-redis),才加载此配置。

3. @ConditionalOnMissingBean:当 Bean 不存在时

@Configuration
public class DataSourceConfig {

    @Bean
    @ConditionalOnMissingBean(DataSource.class)
    public DataSource defaultDataSource() {
        return new HikariDataSource(); // 默认数据源
    }
}

✅ 如果用户没有自定义 DataSource,则使用默认配置;否则,使用用户自定义的。
✅ 这是 Spring Boot 实现“约定优于配置”的关键!

4. @ConditionalOnWebApplication:判断是否为 Web 环境

@Configuration
@ConditionalOnWebApplication(type = Type.SERVLET)
public class WebConfig {
    // 只在 Servlet Web 环境下生效
}

⚠️ 注意事项

事项

建议

⚠️ 条件判断要轻量

matches() 方法不能有复杂 I/O 或阻塞操作

⚠️ 避免循环依赖

条件判断中不要依赖尚未创建的 Bean

⚠️ 合理使用 matchIfMissing

默认值要符合“最小权限”原则

✅ 文档化条件逻辑

让团队成员清楚每个条件的含义

精彩评论(0)

0 0 举报