Java 在运行时选择Springbean
我在选择正确的springbean时遇到了一个问题。 我需要一种方法,根据对前一个类的调用来告诉spring容器注入什么bean。我用xml进行所有Springbean连接 我的问题:这可能吗?它是否是实现的参考 我已经创建了一些示例代码来说明我试图实现的目标。您可以随意更改它,以便在运行时根据所选的reportType注入正确的ReportHeader beanJava 在运行时选择Springbean,java,spring,dependency-injection,Java,Spring,Dependency Injection,我在选择正确的springbean时遇到了一个问题。 我需要一种方法,根据对前一个类的调用来告诉spring容器注入什么bean。我用xml进行所有Springbean连接 我的问题:这可能吗?它是否是实现的参考 我已经创建了一些示例代码来说明我试图实现的目标。您可以随意更改它,以便在运行时根据所选的reportType注入正确的ReportHeader bean public enum ReportType{ Credit, Annul } public class R
public enum ReportType{
Credit,
Annul
}
public class ReportService {
private ReportHeaderService reportHeaderService;
private ReportType reportType;
public ReportService (){}
public setReportType(ReportType reportType){
this.reportType = reportType;
}
public void setReportHeaderService(ReportHeaderService reportHeaderService){
this.reportHeaderService = reportHeaderService;
}
private void generateHeader(){
//i would like to call my service like this and have the correct bean injected to ReportHeader.
reportHeaderService.generateHeader(reportType)
}
}
public class ReportHeaderService {
private ReportHeader reportHeader;
//this will call the injected bean that needs to be selected accoring to the ReportType
public void generateHeader(ReportType type){
reportHeader.createHeader();
}
}
public interface ReportHeader{
public void createHeader();
}
public class CreditReportHeader implements ReportHeader{
public void createHeader(){
..dostuff();
}
}
public class AnnulReportHeader implements ReportHeader{
public void createHeader(){
..dostuff();
}
}
考虑将
Map
注入ReportHeaderService,以便generateHeader的工作方式如下:
public class ReportHeaderService {
private Map<ReportType, ReportHeader> reportHeaderMap;
public void generateHeader(ReportType type){
ReportHeader reportHeader = reportHeaderMap.get(type);
if (reportHeader != null) {
reportHeader.createHeader();
}
}
}
公共类ReportHeaderService{
私有地图报表头映射;
公共无效生成器标头(报表类型){
ReportHeader ReportHeader=reportHeaderMap.get(类型);
if(reportHeader!=null){
reportHeader.createHeader();
}
}
}
考虑向ReportHeaderService注入一个映射,这样generateHeader就可以:
public class ReportHeaderService {
private Map<ReportType, ReportHeader> reportHeaderMap;
public void generateHeader(ReportType type){
ReportHeader reportHeader = reportHeaderMap.get(type);
if (reportHeader != null) {
reportHeader.createHeader();
}
}
}
公共类ReportHeaderService{
私有地图报表头映射;
公共无效生成器标头(报表类型){
ReportHeader ReportHeader=reportHeaderMap.get(类型);
if(reportHeader!=null){
reportHeader.createHeader();
}
}
}
您可以根据ReportType
定义一个ReportHeaderFactory
来获取ReportHeader
:
public class ReportHeaderFactory {
private CreditReportHeader creditReportHeader;
private AnnulReportHeader annulReportHeader;
public ReportHeader getReportHeader(ReportType reportType) {
switch (reportType) {
case Credit:
return creditReportHeader;
case Annul:
return annulReportHeader;
default:
throw new IllegalArgumentException("No Such Header");
}
}
}
使用ReportHeaderFactory
的实例重新定义ReportHeaderService
:
public class ReportHeaderService {
//private ReportHeader reportHeader;
private ReportHeaderFactory headerFactory;
//this will call the injected bean that needs to be selected accoring to the ReportType
public void generateHeader(ReportType type){
//reportHeader.createHeader();
headerFactory.getReportHeader(type);
}
}
在xml中执行所有SpringBean连接时,只需在配置文件中创建以下条目:
<bean id="ReportHeaderService" class="x.y.ReportHeaderService">
<property name="headerFactory" ref="headerFactory" />
</bean>
<bean id="headerFactory" class="x.y.ReportHeaderFactory">
<property name="creditReportHeader" ref="creditReportHeader" />
<property name="annulReportHeader" ref="annulReportHeader" />
</bean>
<bean id="creditReportHeader" class="x.y.CreditReportHeaderImpl" />
<bean id="annulReportHeader" class="x.y.AnnulReportHeaderImpl" />
您可以根据ReportType
定义一个ReportHeaderFactory
来获取ReportHeader
:
public class ReportHeaderFactory {
private CreditReportHeader creditReportHeader;
private AnnulReportHeader annulReportHeader;
public ReportHeader getReportHeader(ReportType reportType) {
switch (reportType) {
case Credit:
return creditReportHeader;
case Annul:
return annulReportHeader;
default:
throw new IllegalArgumentException("No Such Header");
}
}
}
使用ReportHeaderFactory
的实例重新定义ReportHeaderService
:
public class ReportHeaderService {
//private ReportHeader reportHeader;
private ReportHeaderFactory headerFactory;
//this will call the injected bean that needs to be selected accoring to the ReportType
public void generateHeader(ReportType type){
//reportHeader.createHeader();
headerFactory.getReportHeader(type);
}
}
在xml中执行所有SpringBean连接时,只需在配置文件中创建以下条目:
<bean id="ReportHeaderService" class="x.y.ReportHeaderService">
<property name="headerFactory" ref="headerFactory" />
</bean>
<bean id="headerFactory" class="x.y.ReportHeaderFactory">
<property name="creditReportHeader" ref="creditReportHeader" />
<property name="annulReportHeader" ref="annulReportHeader" />
</bean>
<bean id="creditReportHeader" class="x.y.CreditReportHeaderImpl" />
<bean id="annulReportHeader" class="x.y.AnnulReportHeaderImpl" />
这当然是一个可行的解决方案,但我希望避免注入多个bean。这当然是一个可行的解决方案,但我希望避免注入多个bean。这当然是一个可行的解决方案,但我希望避免注入多个bean,因为我想所有的bean都将注入映射,而不仅仅是在映射上调用get后加载?如果您希望它是延迟加载的,那么应该允许您向映射注入延迟加载代理,而不是实际的bean。您可能需要研究的另一件事是decorator模式:您可以创建一个ReportHeader impl,它负责委托createHeader()的工作打电话给正确的人。当然,ReportType需要是createHeader()的一个输入参数这当然是一个可行的解决方案,但我希望避免注入多个bean,因为我猜所有bean都将注入到映射中,而不仅仅是在映射上调用get后才加载?如果希望延迟加载,应该允许您向映射注入延迟加载代理,而不是实际的bean。您可能需要研究的另一件事是decorator模式:您可以创建一个ReportHeader impl,它将createHeader()调用委托给正确的调用。当然,ReportType需要是createHeader()的输入参数