@Conditional可以根据代码中设置的条件装载不同的bean,比如说当一个接口有两个实现类时,我们要把这个接口交给Spring管理时通常会只选择实现其中一个实现类,这个时候我们总不能使用if-else吧,所以这个@Conditional的注解就出现了。
cat
public class Cat {
public Cat(){
System.out.println("this is cat");
}
}
Dog
public class Dog {
public Dog(){
System.out.println("容器加载Dog完成");
}
}
windowsCondition控制类
public class WindowsCondition implements Condition {
/**
*
* @param conditionContext: 判断条件能是用的上下文环境
* @param annotatedTypeMetadata :注解所在位置的注释信息
* @return
*/
@Override
public boolean matches(ConditionContext conditionContext, AnnotatedTypeMetadata annotatedTypeMetadata) {
//获取IOC使用的BeanFactory
ConfigurableListableBeanFactory beanFactory = conditionContext.getBeanFactory();
//获取类加载器
ClassLoader classLoader = conditionContext.getClassLoader();
//获取系统环境
Environment environment = conditionContext.getEnvironment();
String osName = environment.getProperty("os.name");
if(osName.contains("Windows")){
return true;
}
return false;
}
}
LinuxCondition控制类
public class LinuxCondition implements Condition {
/**
*
* @param conditionContext: 判断条件能是用的上下文环境
* @param annotatedTypeMetadata :注解所在位置的注释信息
* @return
*/
@Override
public boolean matches(ConditionContext conditionContext, AnnotatedTypeMetadata annotatedTypeMetadata) {
//获取IOC使用的BeanFactory
ConfigurableListableBeanFactory beanFactory = conditionContext.getBeanFactory();
//获取类加载器
ClassLoader classLoader = conditionContext.getClassLoader();
//获取系统环境
Environment environment = conditionContext.getEnvironment();
String osName = environment.getProperty("os.name");
if(osName.contains("Linux")){
return true;
}
return false;
}
}
配置类
@Configuration
public class MainConfig {
@Conditional(value = {WindowsCondition.class})
@Bean
public Dog dog(){
return new Dog();
}
@Conditional(value = {LinuxCondition.class})
@Bean
public Cat cat(){
return new Cat();
}
}
测试类
public class ConfigurationTest {
public static void main(String[] args) {
ApplicationContext anno = new AnnotationConfigApplicationContext(MainConfig.class);
System.out.println("容器加载完成");
String os = anno.getEnvironment().getProperty("os.name");
System.out.println("当前系统环境为:"+os);
String[] beans = anno.getBeanDefinitionNames();
for ( String bean : beans) {
System.out.println(os+">>>>>beanName:"+bean);
}
}
}
运行结果
windows运行结果
17:05:18.022 [main] DEBUG org.springframework.core.env.PropertySourcesPropertyResolver - Could not find key 'spring.liveBeansView.mbeanDomain' in any property source
容器加载完成
17:05:18.027 [main] DEBUG org.springframework.core.env.PropertySourcesPropertyResolver - Found key 'os.name' in PropertySource 'systemProperties' with value of type String
当前系统环境为:Windows 10
Windows 10>>>>>beanName:org.springframework.context.annotation.internalConfigurationAnnotationProcessor
Windows 10>>>>>beanName:org.springframework.context.annotation.internalAutowiredAnnotationProcessor
Windows 10>>>>>beanName:org.springframework.context.annotation.internalRequiredAnnotationProcessor
Windows 10>>>>>beanName:org.springframework.context.annotation.internalCommonAnnotationProcessor
Windows 10>>>>>beanName:org.springframework.context.event.internalEventListenerProcessor
Windows 10>>>>>beanName:org.springframework.context.event.internalEventListenerFactory
Windows 10>>>>>beanName:mainConfig
Windows 10>>>>>beanName:dog
Linux运行结果
17:05:18.022 [main] DEBUG org.springframework.core.env.PropertySourcesPropertyResolver - Could not find key 'spring.liveBeansView.mbeanDomain' in any property source
容器加载完成
17:05:18.027 [main] DEBUG org.springframework.core.env.PropertySourcesPropertyResolver - Found key 'os.name' in PropertySource 'systemProperties' with value of type String
当前系统环境为:Linux
Linux>>>>>beanName:org.springframework.context.annotation.internalConfigurationAnnotationProcessor
Linux>>>>>beanName:org.springframework.context.annotation.internalAutowiredAnnotationProcessor
Linux>>>>beanName:org.springframework.context.annotation.internalRequiredAnnotationProcessor
Linux>>>>>beanName:org.springframework.context.annotation.internalCommonAnnotationProcessor
Linux>>>>>beanName:org.springframework.context.event.internalEventListenerProcessor
Linux>>>>>beanName:org.springframework.context.event.internalEventListenerFactory
Linux>>>>>beanName:mainConfig
Linux>>>>>beanName:cat
从上面的运行结果来看我们通过@Condition注解中value的LinuxCondition和WindowsCondition两个类来控制cat和dao实例的加载,







网友评论