我有一个简单的POJO:
class MyClass {
int a;
String str;
Strategy strategy;
}
其中,Strategy是一个接口,它具有有限数量的实现,定义为spring singleton bean。我希望从DB中检索此类的对象(对于策略字段,我在表中有一个简单的ID字段)。所以,我想根据表中的ID字段将已经存在的策略实现注入新创建的MyClass实例中。实现这一目标的最佳方法是什么?我考虑过鉴别器,但它总是创建不受spring管理的新实例
答案 0 :(得分:2)
如果我理解正确,我可以提供下一个变体:
为TypeHandler
Type创建MyBatis Strategy
,从spring上下文中获取适当的策略bean。
我希望我没有忘记任何事情。
详细信息:
MyClass {
private Strategy strategy;
}
StrategyA implements Strategy - "a" id in DB
StrategyB implements Strategy - "b" id in DB
1)spring-context.xml:
<bean id="strategyA" class="test.mybatis.inject.StrategyA" scope="singleton"></bean>
<bean id="strategyB" class="test.mybatis.inject.StrategyB" scope="singleton"></bean>
2)创建Spring上下文提供程序:
public class ApplicationContextProvider implements ApplicationContextAware {
private static ApplicationContext context;
public static ApplicationContext getApplicationContext() {
return context;
}
@Override
public void setApplicationContext(ApplicationContext ctx) throws BeansException {
context = ctx;
}
}
3)将提供者bean描述添加到spring-context.xml:
<bean id="applicationContextProvder" class="test.mybatis.inject.ApplicationContextProvider"/>
4)创建StrategyTypeHandler:
@MappedTypes(value={Strategy.class})
public class StrategyTypeHandler implements TypeHandler<Strategy> {
...
public Strategy getResult(ResultSet rs, String columnName) throws SQLException {
switch(rs.getString(columnName)){ //for Java 1.7 & above
case "a":
return (StrategyA)ApplicationContextProvider.getApplicationContext().getBean(StrategyA.class);
case "b":
return (StrategyB)ApplicationContextProvider.getApplicationContext().getBean(StrategyB.class);
}
return null;
}
}
5)MyClassMapper.xml:
<result column="strategy_id" property="strategy" jdbcType="VARCHAR" typeHandler="test.mybatis.inject.StrategyTypeHandler"/>
运行。
答案 1 :(得分:1)
而不是Spring管理的bean,可以用枚举替换策略接口吗?
- 编辑 -
由于您需要Spring管理的bean,因此可以选择探索AOP,因为它可以为容器外部创建的对象启用Spring注入。
请参阅Spring的文档中的here,了解如何将Spring依赖项注入任何对象。
答案 2 :(得分:0)
您可能需要查看
<context:spring-configured />
这将使您实现您想要的目标。