本文知识点来源于尚硅谷,感谢尚硅谷为广大学子提供的优质教育资源,感谢各位老师热情指导,本文仅作为学习笔记使用,记录学习心得,如有不适,请联系作者。
给容器注册组件的方式:
- 包扫描+标注注解 @Controller @Service @Repository @Component 适用于我们自己写的类。
- @Bean,适用于导入第三方包里面的组件。
- @Import ,快速给容器中导入一个组件
1)@Import({Color.class,Red.class})快速给容器导入组件 id默认为全类名 如:cn.tedu.bean.Color
2)ImportSelector 返回值就是导入到容器的组件全类名数组 不能为null
3)ImportBeanDefinitionRegistrar - 使用Spring提供的FactoryBean(工厂bean)
一、@Import 给容器中快速导入一个组件
@Import 导入组件,参数为数组,id默认为全类名
配置类如下:
@Configuration //告诉Spring这是一个配置类
@Import({Color.class})//导入组件,参数为数组,id默认为全类名
public class MainConfig2 {
@Bean//默认单实例Bean
public Person person() {
return new Person("李四",18,"男");
}
}
新增Color类:
public class Color {
}
测试方法如下:
@Test
public void test_Import() {
ApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfig2.class);
String[] beanDefinitionNames = applicationContext.getBeanDefinitionNames();
for (String name : beanDefinitionNames) {
System.out.println(name);
}
}
输出:
org.springframework.context.annotation.internalConfigurationAnnotationProcessor
org.springframework.context.annotation.internalAutowiredAnnotationProcessor
org.springframework.context.annotation.internalCommonAnnotationProcessor
org.springframework.context.event.internalEventListenerProcessor
org.springframework.context.event.internalEventListenerFactory
mainConfig2
com.tedu.bean.Color
person
二、@Import @Import-使用ImportSelector
ImportSelector 返回值就是导入到容器的组件全类名数组 不能为null
新增测试Bean:
public class Blue {
}
public class Yellow {
}
新增自定义选择器:
import org.springframework.context.annotation.ImportSelector;
import org.springframework.core.type.AnnotationMetadata;
/**
* 自定义逻辑返回需要导入的组件
* @author Administrator
*
*/
public class MyImportSelect implements ImportSelector{
/**
* importingClassMetadata
* 当前标注@Import注解类的所有注解信息
*
* @return
* 返回值为导入到容器的组件全类名,切记不能返回Null,会报空指针
*/
@Override
public String[] selectImports(AnnotationMetadata importingClassMetadata) {
return new String[] {"com.tedu.bean.Blue","com.tedu.bean.Yellow"};
}
}
配置类如下,@Import中新增MyImportSelect.class:
@Configuration //告诉Spring这是一个配置类
@Import({Color.class,MyImportSelect.class})//导入组件,参数为数组,id默认为全类名
public class MainConfig2 {
@Bean//默认单实例Bean
public Person person() {
return new Person("李四",18,"男");
}
}
测试类不变,执行并输出:
org.springframework.context.annotation.internalConfigurationAnnotationProcessor
org.springframework.context.annotation.internalAutowiredAnnotationProcessor
org.springframework.context.annotation.internalCommonAnnotationProcessor
org.springframework.context.event.internalEventListenerProcessor
org.springframework.context.event.internalEventListenerFactory
mainConfig2
com.tedu.bean.Color
com.tedu.bean.Blue
com.tedu.bean.Yellow
person
三、@Import 使用ImportBeanDefinitionRegistrar
新增测试Bean:
public class RainBow {
}
新增自定义注册类实现ImportBeanDefinitionRegistrar接口:
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;
import com.tedu.bean.RainBow;
/**
* 自定义注册类
*/
public class MyImportBeanDefinitionRegistrar implements ImportBeanDefinitionRegistrar{
/**
* importingClassMetadata
* 当前类的注解信息
* registry
* BeanDefinition注册类,把所有需要添加到容器中的bean
* 调用BeanDefinitionRegistry.registerBeanDefinition(beanName, beanDefinition)手动注册进来。
*
*/
@Override
public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
//这里是bean id
boolean red = registry.containsBeanDefinition("person");
boolean yellow = registry.containsBeanDefinition("com.tedu.bean.Yellow");
if (red || yellow) {
//指定Bean的定义信息(类型,作用域等)
RootBeanDefinition rootBeanDefinition = new RootBeanDefinition(RainBow.class);
//指定bean id为RainBow1
registry.registerBeanDefinition("RainBow1", rootBeanDefinition);
}
}
}
配置类@Import中加入我们的自定义注册类
@Configuration //告诉Spring这是一个配置类
@Import({Color.class,MyImportSelect.class,MyImportBeanDefinitionRegistrar.class})//导入组件,参数为数组,id默认为全类名
public class MainConfig2 {
}
测试类不变输出:
org.springframework.context.annotation.internalConfigurationAnnotationProcessor
org.springframework.context.annotation.internalAutowiredAnnotationProcessor
org.springframework.context.annotation.internalCommonAnnotationProcessor
org.springframework.context.event.internalEventListenerProcessor
org.springframework.context.event.internalEventListenerFactory
mainConfig2
com.tedu.bean.Color
com.tedu.bean.Blue
com.tedu.bean.Yellow
person
RainBow1
四、使用FactoryBean注册组件
新增自定义工厂bean实现FactoryBean接口
import org.springframework.beans.factory.FactoryBean;
import com.tedu.bean.Color;
public class ColorFacatoryBean implements FactoryBean<Color>{
/**
* 返回对象会添加到容器
*/
@Override
public Color getObject() throws Exception {
return new Color();
}
/**
* 返回Bean类型
*/
@Override
public Class<?> getObjectType() {
return Color.class;
}
/**
* 是否单例
* true 是
*/
@Override
public boolean isSingleton() {
return true;
}
}
配置类:
/**
* 配置类==配置文件xml
* @author Administrator
*
*/
@Configuration //告诉Spring这是一个配置类
public class MainConfig2 {
@Bean()
public ColorFacatoryBean colorFacatoryBean() {
return new ColorFacatoryBean();
}
}
测试方法:
@Test
public void test_FactoryBean() {
ApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfig2.class);
String[] beanDefinitionNames = applicationContext.getBeanDefinitionNames();
for (String name : beanDefinitionNames) {
System.out.println("javaBean名:" + name);
}
System.out.println("=========获取Bean的类型默认为===========");
Object bean = applicationContext.getBean("colorFacatoryBean");
//获取的是调用getObject()返回的对象
System.out.println("bean的类型:" + bean.getClass());
System.out.println("===========判断是否是单例=============");
//调用多次,看是否为单例
Object bean2 = applicationContext.getBean("colorFacatoryBean");
System.out.println(bean == bean2);
System.out.println("=============获取工厂bean本身类型=============");
//如果我只想获取工厂bean本身类型,需要在id前加一个&符
Object bean3 = applicationContext.getBean("&colorFacatoryBean");
System.out.println(bean3);
}
输出:
javaBean名:org.springframework.context.annotation.internalConfigurationAnnotationProcessor
javaBean名:org.springframework.context.annotation.internalAutowiredAnnotationProcessor
javaBean名:org.springframework.context.annotation.internalCommonAnnotationProcessor
javaBean名:org.springframework.context.event.internalEventListenerProcessor
javaBean名:org.springframework.context.event.internalEventListenerFactory
javaBean名:mainConfig2
javaBean名:colorFacatoryBean
=========获取Bean的类型默认为===========
bean的类型:class com.tedu.bean.Color
===========判断是否是单例=============
true
=============获取工厂bean本身类型=============
com.tedu.config.ColorFacatoryBean@7995092a
我们可以看到定义的javaBean名称中虽然有colorFacatoryBean,但是通过getBean()获取的Bean类型却是com.tedu.bean.Color类型,这说明getBean获取的是调用getObject()返回的对象,并且是我们是我们设置的单例,如果想拿到工厂Bean本身类型需要在id前加“&”符号。