怎么把想要的bean(而要注入的bean包括自己项目中的、第三方的)注册到spring容器,让spring替我们管理这些bean呢?
总结起来有四大方式:
一、通过包扫描特定注解的方式
二、@Import 注解
三、@Bean 注解
四、FactoryBean 接口
一、通过包扫描特定注解的方式
特定注解包括:@Controller、@Service、@Component、@Repository。
结合@ComponentScan注解配置相应的路径即可将需要的bean注入容器。
这个之前写过一篇详细的文章,详情见:@ComponentScan配置老扫描不到Bean,这下彻底搞懂!
二、@Import注解
@Import注解注入bean有三种方式:
1.@Import(要注入的bean的class对象),生成的bean的id默认是这个类的全类名
2.@Import(ImportSelector实现类的class对象),导入的组件全类名数组
3.@Import(ImportBeanDefinitionRegistrar实现类的class对象),手动注册需要的bean到容器
比如,我们要导入A、B、C、D、E几个类:
2.1 @Import(要注入的bean的class对象)
可以看到A、B两个类已经注入容器,且id为全类名。
2.2 @Import(ImportSelector实现类的class对象)
可以看到C、D两个类是通过 ImportSelector 接口的实现类 MyImportSelector 注入的。
AnnotationMetadata :@import注解所在类的所有注解信息。这里我们也打印了一下,正好就是 ImportTestConfig02 上面的两个注解:
2.3 @Import(ImportBeanDefinitionRegistrar实现类的class对象)
可以看到,E这个类型的bean是通过 ImportBeanDefinitionRegistrar 接口的实现类 MyRegistry 注入的。且id为类名,非全类名。
三、@Bean 注解
如果要注入的bean来自第三方,类没有使用@Controller、@Service、@Component、@Repository等注解去修饰,那就意味着spring扫描时就不会识别这是个要注入的bean,那就可以使用@bean注解去实现注入:
假设这个CarDTO来自第三方,那就可以这样输入。
四、FactoryBean 接口
可以看到:
1、这里getBean("myFactoryBean"),是小写的,@Bean注解没有指定value时,默认方法名为id
2、@Bean注解是加在返回类型为MyFactoryBean类型的方法上的,但是getBean("myFactoryBean")时返回的bean并不是MyFactoryBean类型的组件,实际返回的是它里面的getObject()方法产生的CarDTO类型的bean
3、因为MyFactoryBean中的isSingleton()方法返回值为true,即单例模式,容器中只有一份实例,多次获取的是同一实例
若把MyFactoryBean中的 isSingleton()方法返回值设为false:
因为MyFactoryBean中的isSingleton()方法返回值为false,即多例模式,每次获取的是不同实例。
好了有了上面的说明,还怕你的bean不能注入吗!