`

ServiceLocatorFactoryBean 学习

 
阅读更多

 

今天看一个新项目的代码, 对里面ServiceLocatorFactoryBean的使用不太明白, 便研究了一番。

 

首先ServiceLocatorFactoryBean的使用场景是这样的, 如果你有一个对象是从spring的beanfactory拿出来,spring的bean一般分为singleton和prototype, singleton是整个spring容器中只有一个实例,prototype是每次注入的时候new一个新实例。但注入一般是注入到对象的属性中,那对于一个对象一般只会注入一次。

假如我每次call一个方法的时候希望都使用的是新的实例, 这时就要靠ServiceLocatorFactoryBean出场了。

官方文档是这样写的

They will typically be used for prototype beans, i.e. for factory methods that are supposed to return a new instance for each call. 

 

 

具体用法是这样的

 

首先定义一个接口用来创建之后要使用的目标对象IPhase

interface IPhaseFactory {
	IPhase getPhase(String name);
}

 

然后设置工厂对象,传入这个接口

  	<beans:bean class="org.springframework.beans.factory.config.ServiceLocatorFactoryBean" id="phaseFactory">
  		<beans:property name="serviceLocatorInterface" value="com.lich.IPhaseFactory"/>
  	</beans:bean>

 

在具体要使用IPhase的对象的类里面设置工厂bean

class PhaseBuilder {

	@Inject
	private IPhaseFactory phaseFactory;


	IPhase build(String name) {
		IPhase phase = phaseFactory.getPhase(name);//这里每次拿到的就是新的对象了
		return phase;
	}

 

 

看代码时这里有个困扰我的问题是 IPhaseFactory接口,  项目代码里面是没有实现类的, spring是在运行时动态代理生成了一个实现类, 那么这里就奇怪了,它怎么知道要用什么样的逻辑来返回我要的那个对象呢,比如 IPhase 接口下面有很多实现类,它怎么知道是哪一个呢?

看下ServiceLocatorFactoryBean类的源码就知道了

		private Object invokeServiceLocatorMethod(Method method, Object[] args) throws Exception {
			Class serviceLocatorMethodReturnType = getServiceLocatorMethodReturnType(method);
			try {
				String beanName = tryGetBeanName(args);
				if (StringUtils.hasLength(beanName)) {
					// Service locator for a specific bean name
					return beanFactory.getBean(beanName, serviceLocatorMethodReturnType);
				}
				else {
					// Service locator for a bean type
					return beanFactory.getBean(serviceLocatorMethodReturnType);
				}
			}
           }


		private String tryGetBeanName(Object[] args) {
			String beanName = "";
			if (args != null && args.length == 1 && args[0] != null) {
				beanName = args[0].toString();
			}
			// Look for explicit serviceId-to-beanName mappings.
			if (serviceMappings != null) {
				String mappedName = serviceMappings.getProperty(beanName);
				if (mappedName != null) {
					beanName = mappedName;
				}
			}
			return beanName;
		}

 上面的代码中会测试着使用接口方法中的参数作为bean的name来去beanfactory里面找, 如果接口方法没有参数,

 

// Service locator for a specific bean name

 return beanFactory.getBean(beanName, serviceLocatorMethodReturnType);

就会使用返回对象的类型来找

 

// Service locator for a bean type

 return beanFactory.getBean(serviceLocatorMethodReturnType);

 

 

那么在我们的列子中就是 用参数中的name来找了

 

IPhase getPhase(String name);

 

比如下面的实现类

@Component("DataPersistPhase")
@Prototype
class DataPersistPhase implements IPhase

 

 

 

0
0
分享到:
评论

相关推荐

    FatoryDe​​sign-Springboot-Batch1

    FatoryDe​​sign-Springboot-Batch1 该设计是使用ServiceLocatorFactoryBean实现的。 当我们有多个接口实现并想在运行时创建bean时,这种方法很方便。 创建一个接口----将由服务实现。 **确保您具有通用类型方法...

    SPRING API 2.0.CHM

    All Classes AbstractAdvisorAutoProxyCreator AbstractApplicationContext AbstractApplicationEventMulticaster AbstractAspectJAdvice AbstractAspectJAdvisorFactory AbstractAspectJAdvisorFactory....

    STM32F103单片机连接EC800-4G模块采集GNSS定位数据和多组传感器数据上传到ONENET云平台并接收控制指令.zip

    1、嵌入式物联网单片机项目开发例程,简单、方便、好用,节省开发时间。 2、代码使用KEIL 标准库开发,当前在STM32F103运行,如果是STM32F103其他型号芯片,依然适用,请自行更改KEIL芯片型号以及FLASH容量即可。 3、软件下载时,请注意keil选择项是jlink还是stlink。 4、有偿指导v:wulianjishu666; 5、如果接入其他传感器,请查看账号发布的其他资料。 6、单片机与模块的接线,在代码当中均有定义,请自行对照。 7、若硬件有差异,请根据自身情况调整代码,程序仅供参考学习。 8、代码有注释说明,请耐心阅读。

    前端分析-2023071100789

    前端分析-2023071100789

    基于python的学生考勤管理系统源代码(完整前后端+mysql+说明文档).zip

    项目均经过测试,可正常运行! 环境说明: 开发语言:python python版本:3.6.8 框架:django 数据库:mysql 5.7/8 数据库工具:navicat 开发软件:pycharm

    基于前端期末大作业源码+文档+高分项目+全部资料.zip

    【资源说明】 基于前端期末大作业源码+文档+高分项目+全部资料.zip 【备注】 1、该项目是个人高分项目源码,已获导师指导认可通过,答辩评审分达到95分 2、该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的,请放心下载使用! 3、本项目适合计算机相关专业(人工智能、通信工程、自动化、电子信息、物联网等)的在校学生、老师或者企业员工下载使用,也可作为毕业设计、课程设计、作业、项目初期立项演示等,当然也适合小白学习进阶。 4、如果基础还行,可以在此代码基础上进行修改,以实现其他功能,也可直接用于毕设、课设、作业等。 欢迎下载,沟通交流,互相学习,共同进步!

    抽象python圣诞树代码动态3d

    python圣诞树代码动态3d

    Python-游戏开发相关代码文件

    Python-游戏开发相关代码文件

    EnglishGrammar.xmind(修正版).zip

    EnglishGrammar.xmind(修正版).zip

    C#实现桌面提醒工具项目

    C#实现桌面提醒工具项目

    基于java+springboot+vue+mysql的党员教育和管理系统 源码+数据库+论文(高分毕业设计).zip

    项目已获导师指导并通过的高分毕业设计项目,可作为课程设计和期末大作业,下载即用无需修改,项目完整确保可以运行。 包含:项目源码、数据库脚本、软件工具等,该项目可以作为毕设、课程设计使用,前后端代码都在里面。 该系统功能完善、界面美观、操作简单、功能齐全、管理便捷,具有很高的实际应用价值。 项目都经过严格调试,确保可以运行!可以放心下载 技术组成 语言:java 开发环境:idea、vscode 数据库:MySql5.7以上 部署环境:maven 数据库工具:navicat

    彩虹外链网盘安装包,内置安装教程

    彩虹外链网盘安装包,内置安装教程

    基于python的文本相似度计算系统(1)源代码(完整前后端+mysql+说明文档+LW).zip

    本系统的主要功能是计算两个文本之间的相似度,具体包括以下几个方面: 提供基于余弦相似度、编辑距离和Jaccard相似度等算法的文本相似度计算功能; 完成文本预处理功能,其中包括去除停用词、分词和词性标注等; 提供文本相似度计算结果的可视化功能,可以直观地展示两个文本之间的相似度。 环境说明: 开发语言:python Python版本:3.6.8 数据库:mysql 5.7 数据库工具:Navicat11 开发软件:pycharm

    VBA-007.批量提取工作表的名字推荐

    VBA-007.批量提取工作表的名字推荐

    STM32F103单片机连接A7680C-4G模块,并支持手机连接WIFI配置修改4G模块远程TCP的目标IP和端口.zip

    1、嵌入式物联网单片机项目开发例程,简单、方便、好用,节省开发时间。 2、代码使用KEIL 标准库开发,当前在STM32F103运行,如果是STM32F103其他型号芯片,依然适用,请自行更改KEIL芯片型号以及FLASH容量即可。 3、软件下载时,请注意keil选择项是jlink还是stlink。 4、有偿指导v:wulianjishu666; 5、如果接入其他传感器,请查看账号发布的其他资料。 6、单片机与模块的接线,在代码当中均有定义,请自行对照。 7、若硬件有差异,请根据自身情况调整代码,程序仅供参考学习。 8、代码有注释说明,请耐心阅读。

    基于opencv dlib的疲劳驾驶检测系统文档+源码+全部资料+优秀项目.zip

    【资源说明】 基于opencv dlib的疲劳驾驶检测系统文档+源码+全部资料+优秀项目.zip 【备注】 1、该项目是个人高分项目源码,已获导师指导认可通过,答辩评审分达到95分 2、该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的,请放心下载使用! 3、本项目适合计算机相关专业(人工智能、通信工程、自动化、电子信息、物联网等)的在校学生、老师或者企业员工下载使用,也可作为毕业设计、课程设计、作业、项目初期立项演示等,当然也适合小白学习进阶。 4、如果基础还行,可以在此代码基础上进行修改,以实现其他功能,也可直接用于毕设、课设、作业等。 欢迎下载,沟通交流,互相学习,共同进步!OpenCV

    深圳建工集团会计主管委派管理办法.docx

    深圳建工集团会计主管委派管理办法

    毕业设计-基于PyQt5的视频播放器设计.rar

    1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、本项目仅用作交流学习参考,请切勿用于商业用途。

    VBA-014.批量工作表破密

    VBA-014.批量工作表破密

    基于小程序的“健康早知道”微信小程序源代码(完整前后端+mysql+LW).zip

    功能说明: 本系统主要包括以下功能模块首页、个人中心、医生管理、用户管理、健康信息管理、健康评估管理、在线留言、系统管理等功能。环境说明: 开发语言:Java 服务器:tomcat7及以上 JDK版本:JDK1.8 数据库:mysql 5.7 数据库工具:Navicat11及以上 开发软件:eclipse/idea 小程序框架:uniapp/原生小程序 开发工具:HBuilder X/微信开发者。。。

Global site tag (gtag.js) - Google Analytics