Distinguish <error-page> view from normal view in ViewHandler#createView()

77 views Asked by At

I have defined error page in my web.xml for error 404 in this way:

<error-page>
    <error-code>404</error-code>
    <location>/common/messages/pageNotFoundError.jsf</location>
</error-page>

Handling invalid page url works as intended - user is redirected to pageNotFoundError page.

I have also defined custom view handler in faces-config.xml. The view handler overrides method createView(FacesContext context, String viewId).

Now is the problem - when a page contains a graphic image with invalid path (which I can't avoid, because users can define paths themselves), the createView method is called twice. Once with viewId = current page id (as I expected) and once with viewId = "/common/messages/pageNotFoundError.jsf". Is there any way to distinguish in createView method "normal" page creation from 404 (or any other) error handling (I don't want to compare viewId strings)? Or maybe the createView method shouldn't be called in this situation - in this case my question is how to change the configuration to achieve this?

1

There are 1 answers

0
BalusC On BEST ANSWER

When the servlet container dispatches to an error page, it will set a bunch of special error page related attributes in the current HTTP servlet request. The keys are identified by those ERROR_XXX constant field values in RequestDispatcher class. Among others, the original request URI for which the error page is being dispatched is available by ERROR_REQUEST_URI key. If this is non-null, then you know that an error page is being dispatched, and you immediately have the original request URI at hands.

In other words,

ExternalContext ec = FacesContext.getCurrentInstance().getExternalContext();
String originalURI = (String) ec.getRequestMap().get(RequestDispatcher.ERROR_REQUEST_URI);

if (originalURI != null) {
    // An error page was dispatched for the given original URI.
} else {
    // We're most likely in the normal flow.
}