JSF 2 Partial Requests не использует FacesContext с завода - PullRequest
2 голосов
/ 15 апреля 2011

Кажется, что частичные запросы не используют экземпляры контекста лица, созданные FacesContextFactory реализациями.

Вот код в UIViewRoot#processDecodes, который указывает то же самое

if (context.getPartialViewContext().isPartialRequest() &&
    !context.getPartialViewContext().isExecuteAll()) {
    context.getPartialViewContext().processPartial(PhaseId.APPLY_REQUEST_VALUES);
} else {
    super.processDecodes(context);
}

Кажется, что PartialViewContext хранит реализацию FacesContextImpl по умолчанию и использует ее для вызова методов жизненного цикла. (Обратите внимание, что метод processPartial не принимает объект контекста, потому что он использует его собственный, хранящийся внутри).

Это ошибка или этот код по определенной причине?

Спасибо

Ответы [ 2 ]

3 голосов
/ 28 мая 2011

FacesContext экземпляры уникальны для каждого потока, и FacesServlet создает ThreadLocal<FacesContext> в начале запроса при получении FacesContext (который является контрактом FacesContextFactory#getFacesContext) и удаляет его в концеответ, связанный с запросом сервлета HTTP (путем вызова FacesContext#release).

Всякий раз, когда вы делаете FacesContext#getCurrentInstance() в своем коде JSF, вы всегда будете получать один и тот же экземпляр во всем запросе сервлета HTTP /обработка ответов.

О методе UIViewRoot#processDecodes я действительно не вижу ни одной строки, которая, вероятно, могла бы указывать, что метод использует собственный созданный экземпляр, а не переданный.Какая линия заставила вас так думать?

В методе FacesServlet#service видно, что он создает FacesContext из FacesContextFactory, вот выдержка из метода FacesServlet#service, которая показывает это -

// Acquire the FacesContext instance for this request
FacesContext context = facesContextFactory.getFacesContext
   (servletConfig.getServletContext(), request, response, lifecycle);

// Execute the request processing lifecycle for this request
try {
 ...
} catch (FacesException e) {
 ...
}
finally {
 // Release the FacesContext instance for this request
 context.release();
}

Учитывая это, я не думаю, что UIViewRoot#processDecodes может иметь экземпляр FacesContext, который не относится к FacesContextFactory.

Поскольку вы говорите - вы установили некоторые дополнительные параметры для FacesContext, которые возвращаются из FacesContextFactory, это означает, что у вас есть собственная пользовательская реализация FacesContextFactory, если это так, тоВы уверены, что ваш экземпляр вводится в FacesServlet, а не в моджарре com.sun.faces.context.FacesContextFactoryImpl (если вы используете моджарру)?

0 голосов
/ 02 декабря 2011

Вот как я заставил это работать.Ниже приведен код в моей фабрике контекста персонализированных лиц

public FacesContext getFacesContext(Object context, Object request, Object response, Lifecycle lifecycle) throws FacesException {
    HttpServletRequest httpRequest = (HttpServletRequest) request;

    ExternalContextFactory externalContextFactory = (ExternalContextFactory) getFactory(FactoryFinder.EXTERNAL_CONTEXT_FACTORY);
    ExternalContext externalContext = externalContextFactory.getExternalContext(context, request, response);

    // CustomFacesContext extends from FacesContextImpl
    CustomFacesContext facesContext = new CustomFacesContext(externalContext, lifecycle);

    ExceptionHandlerFactory exceptionHandlerFactory = (ExceptionHandlerFactory) getFactory(FactoryFinder.EXCEPTION_HANDLER_FACTORY);
    ExceptionHandler exceptionHandler = exceptionHandlerFactory.getExceptionHandler();
    facesContext.setExceptionHandler(exceptionHandler);
}
...