单例 CDI @Inject 空指针异常
Singleton CDI @Inject null pointer exception
我需要使用依赖注入从某些 ejb(无状态和单例)触发事件。我不使用 Spring、Guice 等。
问题是当通过 getInstance() 调用它的方法时,我在其中一个 bean 中得到了 NPE。这是代码片段:
@Stateless
@LocalBean
public class ControllerStartStop {
@Inject
private Event<SomeWebMessage> webEvent;
public String startCircle(String passwordP, String passwordH) {
.........
String res = "some msg";
webEvent.fire(new SomeWebMessage(res, 0)); // this works fine
MainDay.getInstance().startDay(); // NullPointerException
这是 MainDay 单例:
@Singleton
public class MainDay {
private static final MainDay mDay = new MainDay();
public static MainDay getInstance() { return mDay ; }
@Inject
private Event<SomeWebMessage> webEvent;
public void startDay() {
String s = new String("MainDay");
webEvent.fire(new SomeWebMessage(s,0)); // NullPointerException
beans.xml 在 META-INF 中:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
version="1.1" bean-discovery-mode="all">
</beans>
当我从像 MainDay.initDS() 这样的静态方法调用中触发事件时,或者当调度程序调用方法 startDay() 时(@Schedule(hour = " ", 分钟 = "", 秒 = "/10")*。
不知道是什么原因
注意 @Singleton
意味着容器(EJB 或 CDI,取决于它是哪个注释)将管理实例,即 you 不应该创建它你自己。
如果您通过 private static final MainDay mDay = new MainDay();
创建实例,容器将不会进行任何注入,因此 webEvent
将为空。除此之外,容器不会知道该实例,并且在其他地方使用 @Inject MainDay
很可能会产生另一个实例。
因此直接使用注入(或查找,如果需要):
class ControllerStartStop {
@Inject
private MainDay mDay;
...
public String startCircle(String passwordP, String passwordH) {
...
String res = "some msg";
webEvent.fire(new SomeWebMessage(res, 0));
mDay.startDay();
...
}
There is no NPE when I fire event from a call of static method like MainDay.initDS() or when method startDay() is invoked by a Sheduler (@Schedule(hour = "", minute = "", second = "/10")*. I have no idea what is the reason
在不知道您的代码的情况下,这只是一个猜测,但我假设您在此处注入 MainDay
或使用 CDI/JNDI 查找。因此,如果有 none,容器将创建一个实例,并将注入 Event
个对象。
NPE 1:
目标 EJB MainDay
"observe" 事件不应该调用它的 startDay()
方法吗?
public void onEvent(@Observes SomeWebMessage event) {
// if (...)
startDay();
}
因此不需要静态 getInstance()
方法。
NPE 2:
@Inject Event<SomeWebMessage> webEvent;
依赖注入 (DI) 只工作,如果你 不是 手动调用构造函数 new MainDay()
但注入所需 bean 的实例并让 DI 容器处理构造.
但是使用 @Observes
(javax.enterprise.event.Observes) 你应该能够移除所有臭味 static
东西。
我需要使用依赖注入从某些 ejb(无状态和单例)触发事件。我不使用 Spring、Guice 等。 问题是当通过 getInstance() 调用它的方法时,我在其中一个 bean 中得到了 NPE。这是代码片段:
@Stateless
@LocalBean
public class ControllerStartStop {
@Inject
private Event<SomeWebMessage> webEvent;
public String startCircle(String passwordP, String passwordH) {
.........
String res = "some msg";
webEvent.fire(new SomeWebMessage(res, 0)); // this works fine
MainDay.getInstance().startDay(); // NullPointerException
这是 MainDay 单例:
@Singleton
public class MainDay {
private static final MainDay mDay = new MainDay();
public static MainDay getInstance() { return mDay ; }
@Inject
private Event<SomeWebMessage> webEvent;
public void startDay() {
String s = new String("MainDay");
webEvent.fire(new SomeWebMessage(s,0)); // NullPointerException
beans.xml 在 META-INF 中:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
version="1.1" bean-discovery-mode="all">
</beans>
当我从像 MainDay.initDS() 这样的静态方法调用中触发事件时,或者当调度程序调用方法 startDay() 时(@Schedule(hour = " ", 分钟 = "", 秒 = "/10")*。 不知道是什么原因
注意 @Singleton
意味着容器(EJB 或 CDI,取决于它是哪个注释)将管理实例,即 you 不应该创建它你自己。
如果您通过 private static final MainDay mDay = new MainDay();
创建实例,容器将不会进行任何注入,因此 webEvent
将为空。除此之外,容器不会知道该实例,并且在其他地方使用 @Inject MainDay
很可能会产生另一个实例。
因此直接使用注入(或查找,如果需要):
class ControllerStartStop {
@Inject
private MainDay mDay;
...
public String startCircle(String passwordP, String passwordH) {
...
String res = "some msg";
webEvent.fire(new SomeWebMessage(res, 0));
mDay.startDay();
...
}
There is no NPE when I fire event from a call of static method like MainDay.initDS() or when method startDay() is invoked by a Sheduler (@Schedule(hour = "", minute = "", second = "/10")*. I have no idea what is the reason
在不知道您的代码的情况下,这只是一个猜测,但我假设您在此处注入 MainDay
或使用 CDI/JNDI 查找。因此,如果有 none,容器将创建一个实例,并将注入 Event
个对象。
NPE 1:
目标 EJB MainDay
"observe" 事件不应该调用它的 startDay()
方法吗?
public void onEvent(@Observes SomeWebMessage event) {
// if (...)
startDay();
}
因此不需要静态 getInstance()
方法。
NPE 2:
@Inject Event<SomeWebMessage> webEvent;
依赖注入 (DI) 只工作,如果你 不是 手动调用构造函数 new MainDay()
但注入所需 bean 的实例并让 DI 容器处理构造.
但是使用 @Observes
(javax.enterprise.event.Observes) 你应该能够移除所有臭味 static
东西。