3

認証を行うためのフィルターを実装したいのですが、どういうわけか無限ループに陥っています...どんなアイデアでもありがたいです。

    HttpServletRequest httpRequest = (HttpServletRequest) request;
    HttpServletResponse httpResponse = (HttpServletResponse) response;

    doBeforeProcessing(request, response);

    Throwable problem = null;
    HttpSession session = httpRequest.getSession(true);
    if(session.getAttribute("userName")!=null&&session.getAttribute("userName")!=(""))
    {
        try {
            chain.doFilter(request, response);
        } catch (Throwable t) {
            // If an exception is thrown somewhere down the filter chain,
            // we still want to execute our after processing, and then
            // rethrow the problem after that.
            problem = t;
            t.printStackTrace();
        }   
    }else{
        httpResponse.sendRedirect("login.jsp");
        return;
    }

デバッグモードのこのコードは、無限に実行されます。基本的に、ユーザーがログインしていないときに、ユーザーをlogin.jspにリダイレクトします。回答をいただければ幸いです。

4

2 に答える 2

10

ここ、

httpResponse.sendRedirect("login.jsp");

現在のリクエストを使用する代わりに、ターゲット ページの新しいHTTP リクエストを送信しています。この新しい HTTP リクエストは、/*. そして、同じチェックが実行され、再度リダイレクトされます。など。これは終わりのない話です。

FilterChain#doFilter()現在要求されているページがログイン ページである場合にも実行する追加のチェックを追加する必要があります。

String loginURL = httpRequest.getContextPath() + "/login.jsp";

if (httpRequest.getRequestURI().equals(loginURL)) || session.getAttribute("userName") != null) {
    chain.doFilter(request, response);
} else {
    httpResponse.sendRedirect(loginURL);
}

ユーザー名として空の文字列の無意味なチェックも削除したことに注意してください(ただしコードが空の文字列をユーザー名として設定していないことを確認してください。nullログインしていないユーザーを表すために使用するだけです。また、現在要求されている URL がサブフォルダーにある場合は失敗するため、リダイレクト URL も同様です。

別の方法として、制限されたすべてのページを 、 、 などの共通のサブフォルダーに/app配置し、代わりに/secured、、など/restrictedの URL パターンにフィルターをマップします。ログイン ページをこのフォルダの外に置いておくと、ログイン ページが要求されたときにフィルタが呼び出されません。/app/*/secured/*/restricted/*

于 2012-10-29T01:22:38.780 に答える
5

問題は、フィルターが で実行されてlogin.jspおり、ユーザーがログインしていないときに、 が繰り返し自分自身にリダイレクトされることです。フィルターには除外構文がないため、フィルターで URL を検出し、既にページurl-patternにいる場合はリダイレクトを省略する必要があります。login.jsp

    // your auth code
} else {
    String redirect = httpRequest.getContextPath() + "/login.jsp";
    String uri = httpRequest.getRequestURI().toString();
    if (uri.endsWith(redirect)){
        // URI ends with login.jsp, just process the chain
        chain.doFilter();
    } else {
        // not on the login page and not logged in, redirect
        httpResponse.sendRedirect(redirect);
        return;
    }
}
于 2012-10-29T01:23:20.863 に答える