2

こんにちは、Primefaces 4.0 を使用して JSF 2.2.4 プロジェクトに取り組んでいます。

以下の手順を使用して ViewExpiredException を複製しようとしています。

・アプリにブラウザログインする

- 別のタブを開き、ap:menuitem をクリックします (例: 会計画面)。

- サーバーを再起動します (タブの 1 つが自動的にログイン ページにリダイレクトされます)。

- アプリケーションに再度ログインしてから、同じ p:menuitem をもう一度クリックします [突然、ブラウザに jsf ページではなくパーシャル レスポンス xml が表示されます]

ブラウザに表示される XML:

<partial-response>
  <redirect url="/myapplication/denied/viewexpiredpage.jsf"/>
</partial-response>

CustomExceptionHandler.java

public class CustomExceptionHandler extends ExceptionHandlerWrapper {

private Logger logger = LoggerFactory.getLogger(CustomExceptionHandler.class);

private ExceptionHandler wrapped;

CustomExceptionHandler(ExceptionHandler exception) {
    this.wrapped = exception;
}

@Override
public ExceptionHandler getWrapped() {
    return wrapped;
}

@Override
public void handle() throws FacesException {
    FacesContext fc = FacesContext.getCurrentInstance();
    Map<String, Object> requestMap = fc.getExternalContext().getRequestMap();
    NavigationHandler nav = fc.getApplication().getNavigationHandler();

    for (Iterator<ExceptionQueuedEvent> i = getUnhandledExceptionQueuedEvents().iterator(); i.hasNext();) {
        ExceptionQueuedEvent event = i.next();
        ExceptionQueuedEventContext context = (ExceptionQueuedEventContext) event.getSource();
        Throwable t = context.getException();

        try {
            if (t instanceof ViewExpiredException) {
                logger.error("Custom Exception Handler caught an error: " + t.getMessage());
                fc.setViewRoot(fc.getApplication().getViewHandler().createView(fc, "expiredpage"));
                nav.handleNavigation(fc, null, "expiredpage");
                fc.getPartialViewContext().setRenderAll(true);
                fc.renderResponse();
            }else{     
                logger.error("Custom Exception Handler caught an error: " + t.getMessage());
            }
        }finally{
            i.remove();
        }
    }
    // At this point, the queue will not contain any ViewExpiredEvents.
    // Therefore, let the parent handle them.
    getWrapped().handle();
}
}

顔-config.xml

<factory>
    <exception-handler-factory>
        com.pemc.crss.web.commons.exceptionhandler.CustomExceptionHandlerFactory
    </exception-handler-factory>
</factory>

<navigation-rule>
    <from-view-id>*</from-view-id>
    <navigation-case>
        <from-outcome>expiredpage</from-outcome>
        <to-view-id>/denied/viewexpiredpage.jsf</to-view-id>
        <redirect />
    </navigation-case>
</navigation-rule>

ViewExpiredException は例外ハンドラーでキャッチされ、部分応答からの URL は正しいようですが、実際の jsf エラー ページではなく部分応答 xml が表示されるのはなぜですか?

この問題に光を当てるための助けをいただければ幸いです。ありがとう!

4

1 に答える 1

0

ViewHandler#createView()ナビゲーションケース(そこにある「期限切れのページ」)を受け入れません。代わりに、実際のビュー ID またはエラー ページへの相対パスを指定する必要があります。

fc.getApplication().getViewHandler().createView(fc, "/myapplication/denied/viewexpiredpage.jsf");
于 2015-05-29T14:10:19.903 に答える