in impl/src/main/java/org/apache/myfaces/lifecycle/RestoreViewExecutor.java [88:336]
public boolean execute(FacesContext facesContext)
{
if (facesContext == null)
{
throw new FacesException("FacesContext is null");
}
// get some required Objects
Application application = facesContext.getApplication();
ViewHandler viewHandler = application.getViewHandler();
RestoreViewSupport restoreViewSupport = getRestoreViewSupport(facesContext);
ViewIdSupport viewHandlerSupport = getViewIdSupport(facesContext);
// Examine the FacesContext instance for the current request. If it already contains a UIViewRoot
UIViewRoot viewRoot = facesContext.getViewRoot();
if (viewRoot != null)
{
if (log.isLoggable(Level.FINEST))
{
log.finest("View already exists in the FacesContext");
}
// Set the locale on this UIViewRoot to the value returned by the getRequestLocale() method on the
// ExternalContext for this request
viewRoot.setLocale(facesContext.getExternalContext().getRequestLocale());
restoreViewSupport.processComponentBinding(facesContext, viewRoot);
// invoke the afterPhase MethodExpression of UIViewRoot
_invokeViewRootAfterPhaseListener(facesContext);
return false;
}
String viewId = viewHandlerSupport.calculateViewId(facesContext);
// Determine if the current request is an attempt by the
// servlet container to display an error page.
// If the request is an error page request, the servlet container
// is required to set the request parameter "jakarta.servlet.error.message".
final boolean errorPageRequest = facesContext.getExternalContext().getRequestMap()
.get("jakarta.servlet.error.message") != null;
// Determine if this request is a postback or an initial request.
// But if it is an error page request, do not treat it as a postback (since 2.0)
if (!errorPageRequest && restoreViewSupport.isPostback(facesContext))
{ // If the request is a postback
if (log.isLoggable(Level.FINEST))
{
log.finest("Request is a postback");
}
if (checkViewNotFound(facesContext))
{
String derivedViewId = viewHandler.deriveLogicalViewId(facesContext, viewId);
ViewDeclarationLanguage vdl = viewHandler.getViewDeclarationLanguage(facesContext, derivedViewId);
// viewHandler.deriveLogicalViewId() could trigger an InvalidViewIdException, which
// it is handled internally sending a 404 error code set the response as complete.
if (facesContext.getResponseComplete())
{
return true;
}
if (vdl == null || derivedViewId == null)
{
sendSourceNotFound(facesContext, viewId);
return true;
}
else if (!viewHandlerSupport.isViewExistent(facesContext, derivedViewId))
{
sendSourceNotFound(facesContext, viewId);
return true;
}
}
try
{
facesContext.setProcessingEvents(false);
// call ViewHandler.restoreView(), passing the FacesContext instance for the current request and the
// view identifier, and returning a UIViewRoot for the restored view.
viewRoot = viewHandler.restoreView(facesContext, viewId);
if (viewRoot == null)
{
if (facesContext.getResponseComplete())
{
// If the view handler cannot restore the view and the response
// is complete, it can be an error or some logic in restoreView.
return true;
}
else
{
// If the return from ViewHandler.restoreView() is null, throw a ViewExpiredException with an
// appropriate error message.
throw new ViewExpiredException("View \"" + viewId + "\" could not be restored.", viewId);
}
}
// If the view is transient (stateless), it is necessary to check the view protection
// in POST case.
if (viewRoot.isTransient())
{
checkViewProtection(facesContext, viewHandler, viewRoot.getViewId(), viewRoot);
}
// Store the restored UIViewRoot in the FacesContext.
facesContext.setViewRoot(viewRoot);
}
finally
{
facesContext.setProcessingEvents(true);
}
// Restore binding
// See https://javaserverfaces-spec-public.dev.java.net/issues/show_bug.cgi?id=806
restoreViewSupport.processComponentBinding(facesContext, viewRoot);
ClientWindow clientWindow = facesContext.getExternalContext().getClientWindow();
if (clientWindow != null)
{
// The idea of this event is once the client window and the view is initialized,
// you have the information required to clean up any scope that belongs to old
// clientWindow instances like flow scope (in server side state saving).
facesContext.getApplication().publishEvent(facesContext, PostClientWindowAndViewInitializedEvent.class,
clientWindow);
}
}
else
{
// If the request is a non-postback
if (log.isLoggable(Level.FINEST))
{
log.finest("Request is not a postback. New UIViewRoot will be created");
}
String logicalViewId = viewHandler.deriveLogicalViewId(facesContext, viewId);
ViewDeclarationLanguage vdl = viewHandler.getViewDeclarationLanguage(facesContext, logicalViewId);
// viewHandler.deriveLogicalViewId() could trigger an InvalidViewIdException, which
// it is handled internally sending a 404 error code set the response as complete.
if (facesContext.getResponseComplete())
{
return true;
}
if (checkViewNotFound(facesContext))
{
if (vdl == null || logicalViewId == null)
{
sendSourceNotFound(facesContext, viewId);
return true;
}
else if (!viewHandlerSupport.isViewExistent(facesContext, logicalViewId))
{
sendSourceNotFound(facesContext, viewId);
return true;
}
}
if (vdl != null)
{
ViewMetadata metadata = vdl.getViewMetadata(facesContext, viewId);
if (metadata != null)
{
viewRoot = metadata.createMetadataView(facesContext);
if(facesContext.getResponseComplete())
{
// this can happen if the current request is a debug request,
// in this case no further processing is necessary
return true;
}
}
if (viewRoot == null)
{
facesContext.renderResponse();
}
else if (viewRoot != null && !ViewMetadata.hasMetadata(viewRoot))
{
facesContext.renderResponse();
}
}
else
{
// Call renderResponse
facesContext.renderResponse();
}
checkViewProtection(facesContext, viewHandler, logicalViewId, viewRoot);
// viewRoot can be null here, if ...
// - we don't have a ViewDeclarationLanguage (e.g. when using facelets-1.x)
// - there is no view metadata or metadata.createMetadataView() returned null
if (viewRoot == null)
{
// call ViewHandler.createView(), passing the FacesContext instance for the current request and
// the view identifier
viewRoot = viewHandler.createView(facesContext, viewId);
}
if (viewRoot == null && facesContext.getResponseComplete())
{
// If the view handler cannot create the view and the response
// is complete, it can be an error, just get out of the algorithm.
return true;
}
// Subscribe the newly created UIViewRoot instance to the AfterAddToParent event, passing the
// UIViewRoot instance itself as the listener.
// -= Leonardo Uribe =- This line it is not necessary because it was
// removed from jsf 2.0 section 2.2.1 when pass from EDR2 to Public Review
// viewRoot.subscribeToEvent(PostAddToViewEvent.class, viewRoot);
// Store the new UIViewRoot instance in the FacesContext.
facesContext.setViewRoot(viewRoot);
ClientWindow clientWindow = facesContext.getExternalContext().getClientWindow();
if (clientWindow != null)
{
facesContext.getApplication().publishEvent(facesContext, PostClientWindowAndViewInitializedEvent.class,
clientWindow);
}
FlowHandler flowHandler = facesContext.getApplication().getFlowHandler();
if (flowHandler != null)
{
flowHandler.clientWindowTransition(facesContext);
}
// Publish an AfterAddToParent event with the created UIViewRoot as the event source.
application.publishEvent(facesContext, PostAddToViewEvent.class, viewRoot);
}
// add the ErrorPageBean to the view map to fully support
// facelet error pages, if we are in ProjectStage Development
// and currently generating an error page
if (errorPageRequest && facesContext.isProjectStage(ProjectStage.Development))
{
facesContext.getViewRoot().getViewMap()
.put(ErrorPageWriter.ERROR_PAGE_BEAN_KEY, new ErrorPageWriter.ErrorPageBean());
}
// invoke the afterPhase MethodExpression of UIViewRoot
_invokeViewRootAfterPhaseListener(facesContext);
return false;
}