Wildfly 8 和 weld CDI inject via provider 方法不注入依赖
Wildfly 8 and weld CDI inject via provider method does not inject dependecies
我有一个接口和它的实现;
interface MyInterface {
public void doSomething();
}
@Alternative
class MyImpl implements MyInterface {
@Inject DB db;
public void doSomething() {
// db.select ....
}
}
因为我希望能够通过配置文件更改我的数据库,所以我使用提供程序方法来生成实现
@Singleton
public class MyApiProvider {
@Produces
public MyInterface getMyApi() {
return new MyImpl();
}
}
问题是,当 MyImpl class 通过 getMyApi 方法生成时,“@Inject DB db;”在 MyImpl 中 class 为空。
所以我想做的只是能够配置在运行时使用哪个实现。
编辑:
当我删除 @Alternative 并删除提供程序时 class/method 一切都按预期工作..
编辑 2:
我想从配置文件中告诉我的 webapp 我今天想使用 MyInterface 的哪个实现 class。明天也许我想要另一个实现,我不想重新编译整个项目。
这是因为 您 正在创建 MyImpl
class 而不是让 CDI 实现来完成它。
您仅在 CDI 控制对象生命周期时进行注入(和其他注释处理)。
您要找的可能是@Qualifier。
可以在 beans.xml 文件中指定特定的 @Alternative
。
或者,您可以尝试以下方法:
@ApplicationScoped
public class Configuration {
public String getMyInterfaceImpl() {
// property file loading logic
}
}
public class SomeClient {
@Inject @Named("#{configuration.myInterfaceImpl}")
private MyInterface myInterface;
...
}
您可以使用基于 property/parameter:
选择具体实现的生产者方法
@Produces
public MyInterface myInterface(MyImplA a, MyImplB b) {
return (propertyValueA) ? a : b;
}
由于生产者方法需要实例a和b,它们将由容器创建,因此使用注入。
这是一种快速且简化的方法,如果您需要更多变化或实例创建成本高昂,您应该使用 CDI BeanManager 来获取 select 您想要 return 的 bean。
我有一个接口和它的实现;
interface MyInterface {
public void doSomething();
}
@Alternative
class MyImpl implements MyInterface {
@Inject DB db;
public void doSomething() {
// db.select ....
}
}
因为我希望能够通过配置文件更改我的数据库,所以我使用提供程序方法来生成实现
@Singleton
public class MyApiProvider {
@Produces
public MyInterface getMyApi() {
return new MyImpl();
}
}
问题是,当 MyImpl class 通过 getMyApi 方法生成时,“@Inject DB db;”在 MyImpl 中 class 为空。
所以我想做的只是能够配置在运行时使用哪个实现。
编辑: 当我删除 @Alternative 并删除提供程序时 class/method 一切都按预期工作..
编辑 2: 我想从配置文件中告诉我的 webapp 我今天想使用 MyInterface 的哪个实现 class。明天也许我想要另一个实现,我不想重新编译整个项目。
这是因为 您 正在创建 MyImpl
class 而不是让 CDI 实现来完成它。
您仅在 CDI 控制对象生命周期时进行注入(和其他注释处理)。
您要找的可能是@Qualifier。
可以在 beans.xml 文件中指定特定的 @Alternative
。
或者,您可以尝试以下方法:
@ApplicationScoped
public class Configuration {
public String getMyInterfaceImpl() {
// property file loading logic
}
}
public class SomeClient {
@Inject @Named("#{configuration.myInterfaceImpl}")
private MyInterface myInterface;
...
}
您可以使用基于 property/parameter:
选择具体实现的生产者方法@Produces
public MyInterface myInterface(MyImplA a, MyImplB b) {
return (propertyValueA) ? a : b;
}
由于生产者方法需要实例a和b,它们将由容器创建,因此使用注入。
这是一种快速且简化的方法,如果您需要更多变化或实例创建成本高昂,您应该使用 CDI BeanManager 来获取 select 您想要 return 的 bean。