Spring Boot中@Import三种使用方式
转载于:公众号: 后端元宇宙
需要注意的是:ImportSelector、
ImportBeanDefinitionRegistrar这两个接口都必须依赖于@Im
port一起使用,而@Import可以单独使用。
@Import是一个非常有用的注解,它的长处在于你可以通过配置来控制是否注入该Bean,也可以通过条件来控制注入哪些Bean到Spring容器中。
比如我们熟悉的:@EnableAsync 、@EnableCaching、@EnableScheduling等等统一采用的都是借助@Import注解来实现的。
下面我们就通过示例来了解@Import三种用法!
1|0一、引入普通类
有个用户类如下
那么如何通过@Import注入容器呢?
当在@Configuration标注的类上使用@Import引入了一个类后,就会把该类注入容器中。
当然除了@Configuration 比如@Component、@Service等一样也可以。
测试
控制台输出
如果@Import的功能仅仅是这样,那其实它并没什么特别的价值,我们可以通过其它方式实现?
再比如直接添加@Configuration注解
确实如果注入静态的Bean到容器中,那完全可以用上面的方式代替,但如果需要动态的带有逻辑性的注入Bean,那才更能体现@Import的价值。
2|0二、引入ImportSelector的实现类
说到ImportSelector这个接口就不得不说这里面最重要的一个方法:selectImports()。
这个方法的返回值是一个字符串数组,只要在配置类被引用了,这里返回的字符串数组中的类名就会被Spring容器new出来,然后再把这些对象注入IOC容器中。
所以这有啥用呢?我们还是用一个例子演示一下。
3|01、静态import场景(注入已知的类)
我们先将上面的示例改造下:
自定义MyImportSelector实现ImportSelector接口,重写selectImports方法
然后在配置类引用
这样一来同样可以通过成功将UserConfig注入容器中。
如果看到这,你肯定会有疑问。我这又是新建MyImportSelector类,又是实现ImportSelector重写selectImports方法,然后我这么做有个卵用呢?
直接把类上加个@Component注入进去不香吗?这个ImportSelector把简单的功能搞这么复杂。
接下来就要说说如何动态注入Bean了。
4|02、动态import场景(注入指定条件的类)
我们来思考一种场景,就是你想通过开关来控制是否注入该Bean,或者说通过配置来控制注入哪些Bean,这个时候就有了ImportSelector的用武之地了。
我们来举个例子,通过ImportSelector的使用实现条件选择是注入本地缓存还是Redis缓存。
1)、定义缓存接口和实现类
顶层接口
本地缓存 实现类
redis缓存实现类
2)、定义ImportSelector实现类
以下代码中根据EnableMyCache注解中的不同值来切换缓存的实现类再spring中的注册。
3)、定义注解
@EnableMyCache注解就像一个开关,通过这个开关来是否将特定的Bean注入容器。
定义一个枚举
4)、测试
这里选择本地缓存。
控制台输出
切换成redis缓存
控制台输出
这个示例不是就是Bean的动态注入了吗?
5|03、Spring如何使用ImportSelector的场景
SpringBoot有两个常用注解 @EnableAsync @EnableCaching 其实就是通过ImportSelector来动态注入Bean
看下@EnableAsync注解,它有通过@Import({
AsyncConfigurationSelector.class})
AsyncConfigurationSelector.class
是不是和我上面写的示例一样。
总之,向这种还不能决定去注入哪个处理器(如果你能决定,那就直接@Import那个类好了,没必要实现接口了),就可以实现此接口,写出一些判断逻辑,不同的配置情况注入不同的处理类。
6|0三、引入ImportBeanDefinitionRegister的实现类
当配置类实现了
ImportBeanDefinitionRegistrar 接口,你就可以自定义往容器中注册想注入的Bean。
这个接口相比与 ImportSelector 接口的主要区别就是,ImportSelector接口是返回一个类,你不能对这个类进行任何操作,但是
ImportBeanDefinitionRegistrar 是可以自己注入 BeanDefinition,可以添加属性之类的。
7|01、举一个简单的示例
我们通过先通过一个简单的小示例,来理解它的基本使用
假设有个用户配置类如下
我们通过实现
ImportBeanDefinitionRegistrar的方式来完成注入。
通过配置类 中引入MyImportBean对象。
我们再来测试下
控制台输出
说明通过
ImportBeanDefinitionRegistrar方式,已经把UserConfig注入容器成功,而且还为给bean设置了新属性。
然后我们再来思考一个问题,就比如我们在其它地方已经将UserConfig注入容器,这里会不会出现冲突,或者不冲突的情况下,属性能不能设置成功?
我们来试下
然后我们再来跑下上面的测试用例,发现报错了。
8|02、举一个复杂点的例子
Mybatis的@MapperScan就是用这种方式实现的,@MapperScan注解,指定basePackages,扫描Mybatis Mapper接口类注入到容器中。
这里我们自定义一个注解@MyMapperScan来扫描包路径下所以带@MapperBean注解的类,并将它们注入到IOC容器中。
1)、先定义一个@MapperBean注解,就相当于我们的@Mapper注解
2)、一个需要注入的bean,这里加上@MapperBean注解。
3)、再定一个扫描包路径的注解@MyMapperScan 就相当于mybatis的@MapperScan注解。
4)、MyMapperScanImportBean实现
ImportBeanDefinitionRegistrar接口
5)测试
这里扫描的路径就是上面User实体的位置
运行结果
__EOF__

本文链接:https://www.cnblogs.com/caicz/p/16942017.html
关于博主:评论和私信会在第一时间回复。或者直接私信我。
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
声援博主:如果您觉得文章对您有帮助,可以点击文章右下角【推荐】一下。您的鼓励是博主的最大动力!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· .NET10 - 预览版1新功能体验(一)