public interface DateSourceInterFace {//下面两个实现的接口
public void printInfo();
}
@Component
@Profile("dev")
public class DevDateSour implements DateSourceInterFace{
@Override
public void printInfo() {
System.out.println("this DEV profile.......");
}
}
@Component
@Profile("pro")
public class ProDateSour implements DateSourceInterFace{
@Override
public void printInfo() {
System.out.println("this Pro profile.......");
}
}
@ComponentScan//spring扫描到spring容器中创建bean对象
@Configuration
public class ProfileConfig {
}
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = ProfileConfig.class)
@ActiveProfiles("pro")//当前激活pro环境
public class ProfileTest {
@Autowired
private DateSourceInterFace dateSource;
@Test
public void test01(){
dateSource.printInfo();
}
}
结果:
this Pro profile.......
一个xml对象相当于一个配置类;如下有两种方式一种是分别两个xml表示两个环境,第二种是一个xml里面配置两个并设置profile属性,如下就是第二种演示。
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<beans profile="dev">
<bean id="dateSour" class="part03.DevDateSour"/>
beans>
<beans profile="pro">
<bean id="dateSour" class="part03.ProDateSour"/>
beans>
beans>
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {"classpath:/profileContext.xml"})
@ActiveProfiles("pro")
public class ProfileXmlTest {
@Autowired
private DateSourceInterFace dateSource;
@Test
public void test01(){
dateSource.printInfo();
}
}
1、作为DispatcherServlet的初始化参数
2、作为web应用的上下文参数
3、作为环境变量
4、使用@ActiveProfiles激活
下面是web.xml中配置
<context-param>
<param-name>spring.profiles.defaultparam-name>
<param-value>devparam-value>
context-param>
<servlet>
<servlet-name>dispatcherservlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServletservlet-class>
<init-param>
<param-name>spring.profiles.activeparam-name>
<param-value>proparam-value>
init-param>
servlet>
-Dspring.profiles.active="pro"
①如果同时设置了 spring.profile.active=dev 和 spring.profile.default=pro ,只激活dev配置。
②如果没有配置spring.profile.active,只配置了spring.profile.default,才会读取default配置。
③那些没有定义在profile中的bean,任何时候都创建。
@Condition注解的bean,只有满足实现 Condition 接口的 matches 方法才创建,否则忽略。
@Configuration
public class MagicConfig {
@Bean
//MagicExistsCondition类中match方法返回true就穿件如下bean
@Conditional(MagicExistsCondition.class)
public MagicBean magicBean() {
return new MagicBean();
}
}
public class MagicExistsCondition implements Condition {
@Override
public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
Environment env = context.getEnvironment();
return env.containsProperty("magic");
}
}
Condition 接口的matches方法的两个参数
public interface ConditionContext {
//可以检查bean定义
BeanDefinitionRegistry getRegistry();
//检查bean是否存在,检查bean属性
ConfigurableListableBeanFactory getBeanFactory();
//获取环境中存在或者值时多少
Environment getEnvironment();
//获取resourceLoader加载的资源
ResourceLoader getResourceLoader();
//返回累加器,并检查类是否存在
ClassLoader getClassLoader();
}
AnnotatedTypeMetadata 可以检查@bean注解的方法上的其他注解信息。
public interface AnnotatedTypeMetadata {
//
boolean isAnnotated(String annotationName);
Map<String, Object> getAnnotationAttributes(String annotationName);
Map<String, Object> getAnnotationAttributes(String annotationName, boolean classValuesAsString);
MultiValueMap<String, Object> getAllAnnotationAttributes(String annotationName);
MultiValueMap<String, Object> getAllAnnotationAttributes(String annotationName, boolean classValuesAsString);
}
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Conditional(ProfileCondition.class)
public @interface Profile {
/**
* The set of profiles for which the annotated component should be registered.
*/
String[] value();
}
class ProfileCondition implements Condition {
@Override
public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
if (context.getEnvironment() != null) {
//获取@Profile注解的属性value值
MultiValueMap<String, Object> attrs = metadata.getAllAnnotationAttributes(Profile.class.getName());
if (attrs != null) {
for (Object value : attrs.get("value")) {
//从环境中检查是否含有该vlaue值,有则激活该环境,并创建该bean对象
if (context.getEnvironment().acceptsProfiles(((String[]) value))) {
return true;
}
}
return false;
}
}
return true;
}
}