10、组件注册-@Import-使用ImportBeanDefinitionRegistrar
public interface ImportBeanDefinitionRegistrar {
/**
* Register bean definitions as necessary based on the given annotation metadata of
* the importing {@code @Configuration} class.
* <p>Note that {@link BeanDefinitionRegistryPostProcessor} types may <em>not</em> be
* registered here, due to lifecycle constraints related to {@code @Configuration}
* class processing.
* @param importingClassMetadata annotation metadata of the importing class
* @param registry current bean definition registry
*/
public void registerBeanDefinitions(
AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry);
}
10.1 实现ImportBeanDefinitionRegistrar 并重写 registerBeanDefinitionsfan方法
package com.suirui.springanno.condition;
import com.suirui.springanno.entity.RainBow;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.RootBeanDefinition;
import org.springframework.context.annotation.ImportBeanDefinitionRegistrar;
import org.springframework.core.type.AnnotationMetadata;
public class MyImportBeanDefinitionRegistrar implements ImportBeanDefinitionRegistrar {
/**
* @param importingClassMetadata annotation metadata of the importing class 当前类的注解信息
* @param registry current bean definition registry 定义的注册类
* 所有需要添加到容器中的bean BeanDefinitionRegistry.registerBeanDefinition 手动注册进来
*/
public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
boolean red = registry.containsBeanDefinition("com.suirui.springanno.entity.Red");
boolean blue = registry.containsBeanDefinition("com.suirui.springanno.entity.Blue");
//如果容器中已经有red和blue,就创建rainBow
if (red && blue) {
// 指定Bean的定义信息,Bean的类型,作用域等
BeanDefinition beanDefinition = new RootBeanDefinition(RainBow.class);
// 注册一个Bean,指定bean名
registry.registerBeanDefinition("rainBow", beanDefinition);
}
}
}
package com.suirui.springanno.config;
import com.suirui.springanno.condition.LinuxConditional;
import com.suirui.springanno.condition.MyImportBeanDefinitionRegistrar;
import com.suirui.springanno.condition.MyImportSelector;
import com.suirui.springanno.condition.WindowsConditional;
import com.suirui.springanno.entity.Color;
import com.suirui.springanno.entity.Person;
import com.suirui.springanno.entity.Red;
import org.springframework.context.annotation.*;
@Configuration //告诉Spring这是一个配置类
@Import({Color.class, Red.class, MyImportSelector.class, MyImportBeanDefinitionRegistrar.class}) // 快速导入组建,ID 默认是全路径包名
public class MainConfig2 {
@Bean("bill")
@Conditional({WindowsConditional.class})//满足class条件才能生成bean
public Person person1() {
return new Person("bill",38);
}
@Bean("linus")
@Conditional({LinuxConditional.class})//满足class条件才能生成bean
public Person person2() {
return new Person("linus",48);
}
}
package com.suirui.springanno;
import com.suirui.springanno.config.MainConfig;
import com.suirui.springanno.config.MainConfig2;
import com.suirui.springanno.entity.Person;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.core.env.Environment;
import java.util.Map;
public class MainTest {
public static void main(String[] args) {
AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(MainConfig2.class);
//获取所有的BeanDefinitionNames
String[] beanNames = ac.getBeanDefinitionNames();
for (String s : beanNames) {
System.out.println(s);
}
}
}