Using JSF 2.0 / Facelets, is there a way to attach a global listener to all AJAX calls?

后端 未结 2 452
情深已故
情深已故 2020-11-30 09:21

Is there a way to attach a global listener to all AJAX calls in JSF? Maybe through a phase listener or something?

Here is the conundrum... Lets say you\'re using f:a

相关标签:
2条回答
  • 2020-11-30 09:40

    Is there a way to attach a global listener to all AJAX calls in JSF? Maybe through a phase listener or something?

    Yes, a PhaseListener can do it. A SystemEventListener also. A Filter also.

    If you're inside JSF context, then you can check as follows whether the current request is an ajax request or not.

    if (FacesContext.getCurrentInstance().getPartialViewContext().isAjaxRequest()) {
        // It's an ajax request.
    }
    

    If you're not inside JSF context, e.g. inside a Filter, then you can check as follows whether the current request is a JSF ajax request or not.

    if ("partial/ajax".equals(request.getHeader("Faces-Request"))) {
        // It's a JSF ajax request.
    }
    

    Here is the conundrum... Lets say you're using f:ajax tags and something like apache shiro and you let your session expire. Then you come back and click a button that has an f:ajax attached to it. The server will respond with a 302 redirect to the login page.

    The user sees nothing. They can repeatedly click and invoke the ajax call, but to them the app is just "dead."

    Forcing a redirect on an ajax request requires a special XML response. When you're inside JSF context, then ExternalContext#redirect() already takes this implicitly into account. All you need to do is to write this:

    FacesContext.getCurrentInstance().getExternalContext().redirect(url);
    

    If you're not inside JSF context, e.g. inside a Filter, then you'd need to write the whole XML response yourself. E.g.

    response.setContentType("text/xml");
    response.getWriter()
        .append("<?xml version=\"1.0\" encoding=\"UTF-8\"?>")
        .printf("<partial-response><redirect url=\"%s\"></redirect></partial-response>", url);
    
    0 讨论(0)
  • 2020-11-30 10:03

    To redirect a jsf ajax request you need xml as follows

    <?xml version="1.0" encoding="UTF-8"?>   
    <partial-response>  
          <redirect url="XXX">  
          </redirect>  
    </partial-response>
    

    Here XXX is url you want redirect to happen.

    On ajax call redirect sent is not as above hence no redirect.

    To get the desired result have a filter for all jsf request except few pages(login page) and check session is valid and if it is really jsf ajax call by checking header "Faces-Request", its value should be "partial/ajax". If session has expired and is ajax request send above xml as response.

    It should work.

    0 讨论(0)
提交回复
热议问题