我有两个实现我的服务接口的服务,我想在运行时根据某些规则选择正确的服务,例如:
public interface Service { public String doSomething(String param); }
@Component("serviceAimpl")
public class ServiceAImpl implements Service{
public String doSomething(String param){
return param + "A";
}
}
@Component("serviceBimpl")
public class ServiceBImpl implements Service{
public String doSomething(String param){
return param;
}
}
当param以“1”开头并且必须使用ServiceBImpl时必须使用ServiceAImpl,否则,有什么方法可以执行上述操作:
@Component public class ServiceImpl implements Service {
@Autowired private Map<String, Service> services;
public String doSomething(String param) {
if(param.startsWith("1")
return services.get("serviceAimpl").doSomething(param);
else
return services.get("serviceBimpl").doSomething(param);
}
}
这样工厂的类型与bean本身的类型相同,因此不需要创建新类型来获取bean然后使用bean。这在春天有效吗?是否有任何方法或约定来做上面描述的事情(忽略我只在那里连接字符串的事实)?
答案 0 :(得分:1)
我认为您可以使用两个单独的@Autowired
属性,如下所示:
@Service("serviceAimpl")
public class ServiceAImpl implements Service{
public String doSomething(String param){
return param + "A";
}
}
@Service("serviceBimpl")
public class ServiceBImpl implements Service{
public String doSomething(String param){
return param;
}
}
@Service("mainService")
public class ServiceImpl {
@Autowired
private ServiceAImpl serviceAimpl;
@Autowired
private ServiceBImpl serviceBimpl;
public String doSomething(String param) {
if(param.startsWith("1")
return this.serviceAimpl.doSomething(param);
else
return this.serviceBimpl.doSomething(param);
}
}
编辑:如果您想要自动装配地图,列表,这里的一些属性集是一个有趣的article。
答案 1 :(得分:1)
Nikol给出了一个很好的解决方案,我也会这样做。但是不完全了解你的要求,所以你也可能对以下选项感兴趣。
只要预期的键类型为String,即使是类型化的地图也可以自动装配。 Map值将包含所需类型的所有bean,键将包含相应的bean名称:
因此可以获取bean名称和bean,并以你想要的方式使用它
@Autowired
private Map<String, Service > services;
if(somecondition)
services.get("serviceAimpl"). doSomething();
else
services.get("ServiceBImpl"). doSomething()