【问题标题】:JSF logout with ViewScoped bean使用 ViewScoped bean 注销 JSF
【发布时间】:2014-02-14 03:56:16
【问题描述】:

在我的应用程序中,我有一个顶部栏,上面有一个调用 bean 方法的注销按钮

public String logout(){
    FacesContext.getCurrentInstance().getExternalContext().invalidateSession();
    return Navigator.goTo("/index.xhtml");
}

它运作良好,但我有一个特定的页面,它因此异常而失败

2014-01-23T15:17:42.405+0100|WARNING: StandardWrapperValve[Faces Servlet]: Servlet.service() for servlet Faces Servlet threw exception
java.lang.NullPointerException
    at org.jboss.weld.context.beanstore.http.AbstractSessionBeanStore.getLockStore(AbstractSessionBeanStore.java:120)
    at org.jboss.weld.context.beanstore.AttributeBeanStore.lock(AttributeBeanStore.java:219)
    at org.jboss.weld.context.AbstractContext.get(AbstractContext.java:97)
    at org.jboss.weld.context.PassivatingContextWrapper$AbstractPassivatingContextWrapper.get(PassivatingContextWrapper.java:64)
    at org.jboss.weld.bean.proxy.ContextBeanInstance.getInstance(ContextBeanInstance.java:93)
    at org.jboss.weld.bean.proxy.ProxyMethodHandler.invoke(ProxyMethodHandler.java:79)
    at org.omnifaces.cdi.viewscope.ViewScopeManager$Proxy$_$$_WeldClientProxy.preDestroyView(Unknown Source)
    at org.omnifaces.application.ViewScopeEventListener.processEvent(ViewScopeEventListener.java:56)
    at javax.faces.event.SystemEvent.processListener(SystemEvent.java:108)

这个页面和另一个页面之间的唯一区别是这个页面使用了一个 ViewScoped Bean,但我不明白这怎么会是一个问题。解决方案?谢谢

【问题讨论】:

  • 你能解决这个问题吗?

标签: jsf omnifaces view-scope


【解决方案1】:

你试过了吗?

String path = FacesContext.getCurrentInstance().getExternalContext().getApplicationContextPath() + "/index.xhtml";
FacesContext.getCurrentInstance().getExternalContext().invalidateSession();
FacesContext.getCurrentInstance().getExternalContext().redirect(path);

它对我有用...

【讨论】:

    【解决方案2】:

    我遇到了使用 Wildfly9 抛出 NullPointerException 的类似问题。

    当用户登录我们的系统时,我们将他登录,然后我们使他之前的会话无效。问题是当我们使用 CDI SessionScoped bean 时,Wildfly 会给出这个 Stacktrace:

    java.lang.NullPointerException at org.jboss.weld.context.beanstore.http.AbstractSessionBeanStore.getLockStore(AbstractSessionBeanStore.java:112) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.context.beanstore.AttributeBeanStore.lock(AttributeBeanStore.java:209) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.context.AbstractContext.get(AbstractContext.java:90) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.context.PassivatingContextWrapper$AbstractPassivatingContextWrapper.get(PassivatingContextWrapper.java:76) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.bean.ContextualInstanceStrategy$DefaultContextualInstanceStrategy.get(ContextualInstanceStrategy.java:101) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.bean.ContextualInstanceStrategy$CachingContextualInstanceStrategy.get(ContextualInstanceStrategy.java:178) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.bean.ContextualInstance.get(ContextualInstance.java:50) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.bean.proxy.ContextBeanInstance.getInstance(ContextBeanInstance.java:99) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49] at org.jboss.weld.bean.proxy.ProxyMethodHandler.getInstance(ProxyMethodHandler.java:125) [weld-core-impl-2.2.16.SP1.jar:2015-09-16 08:49]

    我什至尝试了How to hunt down obscure HA clustering bug in Wildfly 8.2.0.Final 中提出的解决方案。那里的问题不同,但 Stacktrace 相似,所以我试了一下,但没有成功。

    这没有任何意义。为什么使一个会话无效会导致属于另一个会话范围的 bean 出现问题。这与一个用户登录和另一个用户退出系统基本相同。他们的会话范围 bean 应该完全没有干扰。作为最后的希望,我尝试在另一个线程中执行使先前会话无效的代码并且它起作用了。由于某些未知的原因,创建一个新会话并以相同的方法使其他会话无效会导致 sessionscoped bean 出现问题,但是将它们放在不同的线程中就可以了。

    我希望这可以帮助其他陷入同一问题的人。

    注意: 也许一开始的方法是错误的,我们应该让之前的会话无效,然后让用户登录。还没有测试这个,因为它有很多工作要做。

    【讨论】: