我有一个有状态的会话范围(CDI)EJB,它包含有关用户会话的信息。
@Stateful
@SessionScoped
public class GestorSesion implements IGestorSesionLocal, Serializable {
private final static long serialVersionUID = 1L;
private static final Logger log = Logger.getLogger(GestorSesion.class.getName());
@PostConstruct
private void init() {
log.info("Configurando información de usuario");
log.info("****************************************************************************");
}
@Override
public void cerrarSesion() {
}
@Override
public ISessionInfo getSesionInfo() {
return null;
}
}
现在,我想从cerrarSesion()
closeSession()
( HttpSessionListener
)
public class GestorSesionWeb implements HttpSessionListener {
private static final Logger log = Logger.getLogger(GestorSesionWeb.class.getName());
@Inject
private Instance<IGestorSesionLocal> gestorSesion;
@Override
public void sessionCreated(HttpSessionEvent se) {
if (log.isLoggable(Level.FINE)) {
log.fine("Iniciada sesión web");
}
gestorSesion.get().getSesionInfo();
}
@Override
public void sessionDestroyed(HttpSessionEvent se) {
if (log.isLoggable(Level.FINE)) {
log.fine("Limpiando sesión al salir");
}
try {
this.gestorSesion.get().cerrarSesion();
if (log.isLoggable(Level.FINE)) {
log.fine("Sesión limpiada sin problemas");
}
} catch (Exception e) {
log.log(Level.WARNING, "Excepción limpiando sesión", e);
}
}
}
我从webapp直接访问EJB(使用@EJB
注入)到我用于JSF的bean(它们也是CDI托管bean)。
我面临的问题是HttpSessionListener
似乎与JSF bean处于不同的“会话范围”。创建了GestorSession
的两个实例;一个从JSF实例化,另一个从HttpSessionListener
实例化。
我尝试通过@Inject Instance<IGestorSesionLocal>
,@Inject IGestorSesionLocal
和BeanManager
注入bean,结果相同。
This bug report表明它应该正常工作(错误已经解决了我的版本),但我仍然无法解决它。我环顾四周,但我发现Q&amp; A与JSF托管bean有关(是的,我可以尝试在JSF托管bean中包装对EJB的引用,但我想首先尝试“正确”)。
使用WilFly 8.1.0和JDK 7
有什么想法吗?
答案 0 :(得分:4)
我认为你的pb来自这里:
我直接从webapp访问EJB(使用注入
@EJB
)进入JSF bean。
当使用带有EJB的CDI(例如通过放置@Sessionscoped
)时,你得到的CDI bean也具有EJB性质但不是相反。换句话说,CDI知道EJB的本质,但EJB并不了解CDI。
因此,如果要在代码中将EJB注入CDI bean,请使用@Inject
而不是@EJB
。从Java EE 6开始,承认的良好做法是始终使用@Inject
,除了EJB远程。
还要确保只使用CDI托管bean而不是CDI和JSF托管bean的混合。