Spring学习笔记_20——@Profile
@Profile
1. 解释
在实际开发过程中,可以使用@Profile
隔离开发环境、测试环境和生产环境,每个环境基本上都是互相隔离的。
开发、测试、生产环境的配置信息,不需要通过手动修改,可以通过@Profile
注解实现替换,可以减少项目开发和运维的工作量,可以减少手动修改配置文件导致出现的问题。
使用@Profile
注解时,可以在类或方法上标注,Spring容器在启动时会根据当前激活的profile来决定是否创建和注册这些Bean。
2. 场景
- 环境特定的配置:在不同的环境(如开发、测试、生产环境)中,可能需要加载不同的配置。使用
@Profile
注解可以指定某些Bean只在特定的环境被创建。 - 功能模块的激活:在大型应用中,可能有一些功能模块只在特定的条件下启用。通过
@Profile
注解,可以控制这些模块的激活。 - 条件化的Bean定义:在某些情况下,可能需要根据不同的条件来定义不同的Bean。
@Profile
注解允许开发者根据不同的配置文件来定义和注册Bean。 - 集成测试:在进行集成测试时,可能需要模拟某些环境或条件。
@Profile
注解可以用来定义只在测试环境中激活的Bean。 - 特性开关:在某些特性还未准备好发布到生产环境时,可以使用
@Profile
注解来控制这些特性的开关。 - 多环境配置分离:在微服务架构中,不同的服务可能需要根据不同的环境来配置不同的Bean。
@Profile
注解可以帮助实现这种配置的分离。
3. 源码
package org.springframework.context.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.core.env.AbstractEnvironment;
import org.springframework.core.env.ConfigurableEnvironment;
import org.springframework.core.env.Profiles;
import org.springframework.context.annotation.Conditional;
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Conditional(ProfileCondition.class)
public @interface Profile {
// 指定环境的标识
String[] value();
}
4. Demo
- 注解使用在类上,根据环境配置
@Configuration
@Profile("dev") // 只在开发环境激活
public class DevConfig {
@Bean
public DataSource dataSource() {
// 返回开发环境的DataSource
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.H2)
.addScript("classpath:schema-dev.sql")
.addScript("classpath:data-dev.sql")
.build();
}
}
@Configuration
@Profile("prod") // 只在生产环境激活
public class ProdConfig {
@Bean
public DataSource dataSource() {
// 返回生产环境的DataSource
return new DriverManagerDataSource("jdbc:mysql://localhost:3306/mydb", "user", "pass");
}
}
- 注解使用在方法上
@Configuration
public class FeatureToggleConfig {
@Bean
@Profile("featureXEnabled")
public FeatureX featureX() {
return new FeatureX();
}
@Bean
@Profile({"!featureXEnabled"})
public FeatureY featureY() {
return new FeatureY();
}
}
- 注解使用在类上,根据环境生成指定的Bean
@Component
@Profile("dev") // 只在开发环境激活
public class DevComponent {
public void printDevInfo() {
System.out.println("This is a development component.");
}
}
@Component
@Profile("prod") // 只在生产环境激活
public class ProdComponent {
public void printProdInfo() {
System.out.println("This is a production component.");
}
}
- 组合使用@Profile注解
@Configuration
@Profile({"dev", "test"}) // 只在开发和测试环境激活
public class DevAndTestConfig {
// 配置信息
}