通过筛选设置FacesMessage

Zaw*_* oo 5 java jsf message servlet-filters

在我的JSF应用程序中,有一个Filter用于检查authenticati0n进程.身份验证失败时,筛选器重定向到login.xhtml.

如何FacesMessage从我的登录页面传递Filter

虽然,我在下面使用,但不行.

FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_ERROR, message, null));
Run Code Online (Sandbox Code Playgroud)

AuthenticationFilter.java

public class AuthenticationFilter implements Filter  {
    private FilterConfig config;
    private ServletContext servletContext;

    public void init(FilterConfig filterConfig) {
        config = filterConfig;
        servletContext = config.getServletContext();
    }

    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest httpRequest = (HttpServletRequest) servletRequest;
        HttpServletResponse httpResponse = (HttpServletResponse) servletResponse;
        HttpSession session = httpRequest.getSession();
        User user = (User) session.getAttribute(Constants.LOGIN_USER);
        if (user == null) {
            ...
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_ERROR, message, null));

            String loginView = httpRequest.getContextPath() + Constants.LOGIN_PAGE;
            httpResponse.sendRedirect(loginView);
        } else if (!user.getRole().equals(Role.SYSTEM_ADMINISTRATOR)) {
            ....
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_ERROR, message, null));

            String loginView = httpRequest.getContextPath() + Constants.LOGIN_PAGE;
            httpResponse.sendRedirect(loginView);
        } else {
            filterChain.doFilter(servletRequest, servletResponse);
        }
        servletContext.log("Exiting the filter");
    }

    public void destroy() {
        //Nothing to do.
    }
}
Run Code Online (Sandbox Code Playgroud)

Bal*_*usC 8

由... FacesContext创建FacesServlet.当你进入过滤器时,它尚未被调用.过滤器在servlet之前运行.所以你永远无法接触到FacesContext过滤器.另外,面部消息是请求作用域,因此重定向会使它们无论如何都会消失.

让它login.xhtml在一个时间内自己设定<f:event type="preRenderView">.最简单的方法是让过滤器暂时将它放在会话范围内.

session.setAttribute("message", message);
httpResponse.sendRedirect(loginView);
Run Code Online (Sandbox Code Playgroud)

然后,您在预渲染视图侦听器方法中从会话范围中删除login.xhtml:

String message = (String) externalContext.getSessionMap().remove("message");

if (message != null) {
    context.addMessage(null, new FacesMessage(FacesMessage.SEVERITY_ERROR, message, null));
}
Run Code Online (Sandbox Code Playgroud)