shrio session過期跳轉到登錄頁面問題

一般情況下 shiro在session過期,權限驗證不通過都會跳轉到登錄頁面,但是我的項目中使用了easyui框架,跳轉後並沒有跳轉到登錄頁面,但是在頁面查看網絡請求確實跳轉到登錄頁面,但是頁面並不加載,經過排查問題如下:

問題1:session失效沒有跳轉到登錄頁面

1)排查shiro的配置文件登錄設置正確

//如果不設置,默認自動尋找web工程根目錄下的“login.jsp”頁面
        shiroFilterFactoryBean.setLoginUrl("/login");

2)查看瀏覽器是否重定向到登錄頁面

已經重定向到登錄頁面頁面,而且還不是一個。

3)經過排查發現加載的login不是在框架的頂部,通過發下在重定向的時候要top.localhost.href纔可以重定向,但是咱們去修改shiro是他的重定向加上top呢,通過查看shiro源碼 發現所有的攔截驗證不通過都要走FormAuthenticationFilter過濾器。

在FormAuthenticationFilter中對方法

onAccessDenied進行重寫

源碼:


protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception {
    //判斷是不是登錄請求
        if (isLoginRequest(request, response)) {
            if (isLoginSubmission(request, response)) {
                if (log.isTraceEnabled()) {
                    log.trace("Login submission detected.  Attempting to execute login.");
                }
                return executeLogin(request, response);
            } else {
                if (log.isTraceEnabled()) {
                    log.trace("Login page view.");
                }
                //allow them to see the login page ;)
                return true;
            }
        } else {
//不是登錄請求
            if (log.isTraceEnabled()) {
                log.trace("Attempting to access a path which requires authentication.  Forwarding to the " +
                        "Authentication url [" + getLoginUrl() + "]");
            }

            saveRequestAndRedirectToLogin(request, response);
            return false;
        }
    }

我們對不是登錄請求的方法進行重寫

public class ShiroFormAuthenticationFilter extends FormAuthenticationFilter {
    public static final String DEFAULT_PATH_SEPARATOR = "/";

    private String pathSeparator = DEFAULT_PATH_SEPARATOR;
  /*  @Override
    protected boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) {
        return false;
    }*/

    /**
     * 重寫驗證失效後
     * @param request
     * @param response
     * @return
     * @throws Exception
     */
    @Override
    protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception {
        if (isLoginRequest(request, response)) {
            if (isLoginSubmission(request, response)) {
                return executeLogin(request, response);
            } else {
                return true;
            }
        } else {
            String requestURI = getPathWithinApplication(request);
            System.out.println(requestURI);
            HttpServletRequest httpServletRequest = (HttpServletRequest)request;
            System.out.println(httpServletRequest.getContextPath());
             String[] pattDirs = StringUtils.tokenizeToStringArray(requestURI, this.pathSeparator);
            //是ajax請求重定向
            if(isAjax(request)){
                //if(pattDirs.length>0&&!"system".equals(pattDirs[0])) {
                    PrintWriter out = response.getWriter();
                    out.println("8888");
                //}
            }else{
//針對前段請求window.location.href
                if(requestURI!=null&&requestURI.contains("/doc")){
                    response.setContentType("textml;charset=gb2312");
                    PrintWriter out = response.getWriter();
                    out.println("<script language='javascript' type='text/javascript'>");
                    out.println("alert('由於你長時間沒有操作,導致Session失效!請你重新登錄!');top.location.href='"+httpServletRequest.getContextPath()+"/login'");
                    out.println("</script>");
                }else {
//針對Form表單提交
                    this.saveRequestAndRedirectToLogin(request, response);
                }
            }

            return false;
        }
    }
    private static boolean isAjax(ServletRequest request){
        String header = ((HttpServletRequest) request).getHeader("X-Requested-With");
        if("XMLHttpRequest".equalsIgnoreCase(header)){
            return Boolean.TRUE;
        }
        return Boolean.FALSE;
    }



}

我們發現這個重寫的類並沒有進行加載

需要在shiro的配置文件中進行過濾配置

在shiroConfig.java中配置
 

//自定義過濾類
        ShiroFormAuthenticationFilter shiroFormAuthenticationFilter = new ShiroFormAuthenticationFilter();
        Map<String,Filter> filterMap = new HashMap<>();
        filterChianDefintionMap.put("/**","user,authc");
        filterMap.put("user",shiroFormAuthenticationFilter);
        shiroFilterFactoryBean.setFilters(filterMap);

這樣在shiro加載的時候加載了這個Filter

js修改

針對Form提交重定向後 頁面不能加載問題,在登錄頁做一下改動

 $(function(){
            if(top==window){
            }else{
                top.alert("由於你長時間沒有操作,導致Session失效!請你重新登錄!",top.location.reload())
            }
        })

針對ajax請求js做的改動

在首頁中加

$(function(){
            $.ajaxSetup({
                complete:function(XMLHttpRequest){
                    console.log("sessionStorage:"+sessionStorage.getItem("itemvalue"));
                    if(XMLHttpRequest.responseText==8888&&(sessionStorage.getItem("itemvalue")==null||
                            (new Date().getTime()-sessionStorage.getItem("itemvalue")>100000))){
                        top.alert("由於你長時間沒有操作,導致Session失效!請你重新登錄!",top.location.href= ctx + "/login");
                        sessionStorage.setItem("itemvalue",new Date().getTime());
                    };

                }
            })
        })

對ajax請求加默認參數

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章