JSF页面元素无法使用action属性从支持bean触发方法。(JSF2.0 + primefaces)

时间:2011-04-20 09:58:03

标签: java jsf java-ee jsf-2 primefaces

我有一个带有menuitem元素的primefaces dock导航栏,它应该触发我的web应用程序的注销机制,但它不起作用,我不知道为什么。有人帮我找到了点击菜单项时没有调用注销功能的原因吗?

这是JSF页面模板的元素:

<h:form>
    <p:dock position="top">
    <p:menuitem value="Logout" icon="unsecuredimages/logout.png" action="securityController.logOut()" rendered ="#{!securityController.checkLogged}"/>

    </p:dock>   
</h:form>

这是logOut()方法所在的辅助bean:

@ManagedBean
@RequestScoped
public class SecurityController {

...

public String logOut() {
        authentificationEJB.releaseUserState();     
        return "main.xhtml";
    }

...

这是访问会话并从已登录用户释放它的EJB:

@Stateful(name = "ejbs/AuthentificationEJB")
public class AuthentificationEJB implements IAuthentificationEJB {
...
// Logout
    public void releaseUserState() {
        // 1-Check if there is something saved in the session(or wherever the
        // state is saved)
        if (!FacesContext.getCurrentInstance().getExternalContext()
                .getSessionMap().isEmpty()) {
            // 2-If 1 then flush it
            FacesContext.getCurrentInstance().release();
        }       
    }
    ...
    }

当我点击menuItem时,我得到了这个例外:

  

警告:StandardWrapperValve [面孔   Servlet]:PWC1406:Servlet.service()   for servlet Faces Servlet扔了   例外   java.lang.IllegalStateException at   com.sun.faces.context.FacesContextImpl.assertNotReleased(FacesContextImpl.java:639)     在   com.sun.faces.context.FacesContextImpl.getCurrentPhaseId(FacesContextImpl.java:515)     在   javax.faces.event.ExceptionQueuedEventContext。(ExceptionQueuedEventContext.java:148)     在   javax.faces.event.ExceptionQueuedEventContext。(ExceptionQueuedEventContext.java:101)     在   com.sun.faces.lifecycle.Phase.queueException(Phase.java:156)     在   com.sun.faces.lifecycle.Phase.queueException(Phase.java:149)     在   com.sun.faces.lifecycle.Phase.doPhase(Phase.java:109)     在   com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)     在   javax.faces.webapp.FacesServlet.service(FacesServlet.java:312)     在   org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1523)     在   org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:343)     在   org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:215)     在   filters.RestrictPageFilter.doFilter(RestrictPageFilter.java:90)     在   org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:256)     在   org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:215)     在   org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:277)     在   org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:188)     在   org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:641)     在   com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:97)     在   com.sun.enterprise.web.PESessionLockingStandardPipeline.invoke(PESessionLockingStandardPipeline.java:85)     在   org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:185)     在   org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:325)     在   org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:226)     在   com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:165)     在   com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:791)     在   com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:693)     在   com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:954)     在   com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:170)     在   com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:135)     在   com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:102)     在   com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:88)     在   com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:76)     在   com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:53)     在   com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:57)     在   com.sun.grizzly.ContextTask.run(ContextTask.java:69)     在   com.sun.grizzly.util.AbstractThreadPool $ Worker.doWork(AbstractThreadPool.java:330)     在   com.sun.grizzly.util.AbstractThreadPool $ Worker.run(AbstractThreadPool.java:309)     在   java.lang.Thread.run(Thread.java:662)

更新

<p:menuitem value="Logout" icon="unsecuredimages/logout.png" action="#{securityController.logOut}" rendered ="#{!securityController.checkLogged}"/>

@ManagedBean
@ViewScoped
public class SecurityController {

    @EJB
    private IAuthentificationEJB authentificationEJB;
    private String email;
    private String password;
    private String notificationValue;



    public String logOut() {
         HttpSession session = (HttpSession) FacesContext.getCurrentInstance().getExternalContext().getSession(false);
            if (session != null) {
                session.invalidate();
            }
        return "main.xhtml";
    }

    ...
}

2 个答案:

答案 0 :(得分:1)

我不知道您是否需要release()方法。我认为这种方法是您例外的原因。来自javadoc

的引用
  

在a上调用release()之后   FacesContext实例(直到   FacesContext实例已经   通过实施回收   重复使用),调用任何其他方法   将导致IllegalStateException   被抛出。

     

...

     

实施必须致电   setCurrentInstance(javax.faces.context.FacesContext)   传递null以删除关联   这个线程和这个死之间   FacesContext实例。

我使用以下注销方法。也许这对你有帮助:

public String logout() {
    HttpSession session = (HttpSession) FacesContext.getCurrentInstance().getExternalContext().getSession(false);
    if (session != null) {
        session.invalidate();
    }
    user = null; // reset user
    // optional: addSuccessMessage

    return "login";
}

答案 1 :(得分:-1)

尝试从RequestScoped更改为例如Sessions,我在使用RequestScoped支持bean的apst中遇到了一些麻烦。