我在faces-config.xml中添加了一个faces-config.xml
<lifecycle>
<phase-listener>com.project.NotificationListener</phase-listener>
</lifecycle>这个类似乎在其他方面是正确的,因为它非常简单。
public class NotificationListener implements PhaseListener {
@Inject
private MyCDIStuff stuff;
@Override
public PhaseId getPhaseId() {
return PhaseId.RENDER_RESPONSE;
}
@Override
public void beforePhase(PhaseEvent event) {
this.stuff.doStuff();
}
}“beforePhase”方法被正确调用,但是MyCDIStuff对象为null。我尝试对类使用注释@Singleton,这很可能是不正确的,而且它也无法使注入工作。
有没有办法在PhaseListener中注入CDI托管bean?
发布于 2013-11-12 13:23:13
在JSF2.2之前,PhaseListener没有注册为CDI注入目标。使用@Inject (和@EJB)实际上对PhaseListener没有任何影响。您需要通过编程方式计算引用@Named(隐式)名称的EL表达式,或者通过JNDI和BeanManager (相当笨拙)作为最后手段来手动获取CDI托管bean。
因此,如果您不能升级到JSF2.2(应该与任何JSF2.0/2.1和Servlet3.0兼容的web应用程序兼容),那么最好的方法是编程地评估引用@Named名称的EL表达式。假设你有一个
@Named("stuff")
public class MyCDIStuff {}那么,这应该可以做到:
FacesContext context = event.getFacesContext();
MyCDIStuff stuff = context.getApplication().evaluateExpressionGet(context, "#{stuff}", MyCDIStuff.class);
// ...发布于 2013-11-12 15:29:05
如果不能使用JSF2.2,最好的选择是使用Deltaspike。
它提供MyCDIStuff myCDIStuff = BeanProvider.getContextualReference(MyCDIStuff.class, false);
德尔塔斯派克是你应该得到的东西,而不是自己发明的。例如,如果您必须拥有BeanManager (例如,触发一个事件),那么Deltaspike也提供了BeanManagerProvider。
http://deltaspike.apache.org/core.html
https://stackoverflow.com/questions/19930241
复制相似问题