Home >Java >javaTutorial >Spring+SpringMVC+MyBatis in-depth learning and construction (17) - SpringMVC interceptor

Spring+SpringMVC+MyBatis in-depth learning and construction (17) - SpringMVC interceptor

PHP中文网
PHP中文网Original
2017-07-03 17:30:261458browse

Please indicate the source:

As mentioned earlier: Spring+SpringMVC+MyBatis in-depth learning and construction (16) - SpringMVC annotation development (advanced)

1.Interceptor definition

Spring Web MVC's processor interceptor is similar to the filter Filter in Servlet development, which is used to pre-process and post-process the processor.

Define the interceptor and implement the HandlerInterceptor interface. Three methods are provided in the interface.

<span style="color: #0000ff">package</span><span style="color: #000000"> joanna.yan.ssm.interceptor;

</span><span style="color: #0000ff">import</span><span style="color: #000000"> javax.servlet.http.HttpServletRequest;
</span><span style="color: #0000ff">import</span><span style="color: #000000"> javax.servlet.http.HttpServletResponse;
</span><span style="color: #0000ff">import</span><span style="color: #000000"> org.springframework.web.servlet.HandlerInterceptor;
</span><span style="color: #0000ff">import</span><span style="color: #000000"> org.springframework.web.servlet.ModelAndView;

</span><span style="color: #0000ff">public</span> <span style="color: #0000ff">class</span> HandlerInterceptor1 <span style="color: #0000ff">implements</span><span style="color: #000000"> HandlerInterceptor{

    </span><span style="color: #008000">//</span><span style="color: #008000">执行Handler完成执行此方法
    </span><span style="color: #008000">//</span><span style="color: #008000">应用场景:统一异常处理,统一日志处理</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">void</span><span style="color: #000000"> afterCompletion(HttpServletRequest request,
            HttpServletResponse response, Object handler, Exception ex)
            </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......afterCompletion"<span style="color: #000000">);
    }

    </span><span style="color: #008000">//</span><span style="color: #008000">进入Handler方法之后,返回modelAndView之前执行
    </span><span style="color: #008000">//</span><span style="color: #008000">应用场景从modelAndView出发:将公用的模型数据(比如菜单导航)在这里传到视图,也可以在这里同意指定视图</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">void</span><span style="color: #000000"> postHandle(HttpServletRequest request, HttpServletResponse response,
            Object handler, ModelAndView modelAndView) </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......postHandle"<span style="color: #000000">);
    }

    </span><span style="color: #008000">//</span><span style="color: #008000">进入Handler方法之前执行
    </span><span style="color: #008000">//</span><span style="color: #008000">用于身份认证、身份授权
    </span><span style="color: #008000">//</span><span style="color: #008000">比如身份认证,如果认证不通过表示当前用户没有登录,需要此方法拦截不再向下执行。</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">boolean</span><span style="color: #000000"> preHandle(HttpServletRequest request, HttpServletResponse response,
            Object handler) </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......preHandle"<span style="color: #000000">);
        </span><span style="color: #008000">//</span><span style="color: #008000">return false表示拦截,不向下执行
        </span><span style="color: #008000">//</span><span style="color: #008000">return true表示放行</span>
        <span style="color: #0000ff">return</span> <span style="color: #0000ff">true</span><span style="color: #000000">;
    }

}</span>

2.Interceptor configuration

There is a large interceptor chain in struts. It is a common thing. You can add it to any action link and let it intercept. But spring's interceptor is not global.

2.1 Configure an interceptor for a certain mapping

The springmvc interceptor performs interception settings for HandlerMapping. If interception is set in a HandlerMapping, the handler that is successfully mapped by the HandlerMapping will eventually use the interceptor.

<span style="color: #0000ff"><</span><span style="color: #800000">bean
    </span><span style="color: #ff0000">class</span><span style="color: #0000ff">="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"</span><span style="color: #0000ff">></span>
    <span style="color: #0000ff"><</span><span style="color: #800000">property </span><span style="color: #ff0000">name</span><span style="color: #0000ff">="interceptors"</span><span style="color: #0000ff">></span>
        <span style="color: #0000ff"><</span><span style="color: #800000">list</span><span style="color: #0000ff">></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">ref </span><span style="color: #ff0000">bean</span><span style="color: #0000ff">="handlerInterceptor1"</span><span style="color: #0000ff">/></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">ref </span><span style="color: #ff0000">bean</span><span style="color: #0000ff">="handlerInterceptor2"</span><span style="color: #0000ff">/></span>
        <span style="color: #0000ff"></</span><span style="color: #800000">list</span><span style="color: #0000ff">></span>
    <span style="color: #0000ff"></</span><span style="color: #800000">property</span><span style="color: #0000ff">></span>
<span style="color: #0000ff"></</span><span style="color: #800000">bean</span><span style="color: #0000ff">></span>
    <span style="color: #0000ff"><</span><span style="color: #800000">bean </span><span style="color: #ff0000">id</span><span style="color: #0000ff">="handlerInterceptor1"</span><span style="color: #ff0000"> class</span><span style="color: #0000ff">="joanna.yan.ssm.interceptor.HandlerInterceptor1"</span><span style="color: #0000ff">/></span>
    <span style="color: #0000ff"><</span><span style="color: #800000">bean </span><span style="color: #ff0000">id</span><span style="color: #0000ff">="handlerInterceptor2"</span><span style="color: #ff0000"> class</span><span style="color: #0000ff">="joanna.yan.ssm.interceptor.HandlerInterceptor2"</span><span style="color: #0000ff">/></span>

Generally not recommended.

2.2 Configure global interceptors for all mappings

springmvc can configure similar global interceptors, and the springmvc framework injects the configured global-like interceptors into each HandlerMapping.

    <span style="color: #008000"><!--</span><span style="color: #008000">拦截器 </span><span style="color: #008000">--></span>
    <span style="color: #0000ff"><</span><span style="color: #800000">mvc:interceptors</span><span style="color: #0000ff">></span>
        <span style="color: #008000"><!--</span><span style="color: #008000">多个拦截器,顺序执行 </span><span style="color: #008000">--></span>
        <span style="color: #0000ff"><</span><span style="color: #800000">mvc:interceptor</span><span style="color: #0000ff">></span>
            <span style="color: #008000"><!--</span><span style="color: #008000"> /**表示所有url包括子url路径 </span><span style="color: #008000">--></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">mvc:mapping </span><span style="color: #ff0000">path</span><span style="color: #0000ff">="/**"</span><span style="color: #0000ff">/></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">bean </span><span style="color: #ff0000">class</span><span style="color: #0000ff">="joanna.yan.ssm.interceptor.HandlerInterceptor1"</span><span style="color: #0000ff">></</span><span style="color: #800000">bean</span><span style="color: #0000ff">></span>
        <span style="color: #0000ff"></</span><span style="color: #800000">mvc:interceptor</span><span style="color: #0000ff">></span>
        <span style="color: #0000ff"><</span><span style="color: #800000">mvc:interceptor</span><span style="color: #0000ff">></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">mvc:mapping </span><span style="color: #ff0000">path</span><span style="color: #0000ff">="/**"</span><span style="color: #0000ff">/></span>
            <span style="color: #0000ff"><</span><span style="color: #800000">bean </span><span style="color: #ff0000">class</span><span style="color: #0000ff">="joanna.yan.ssm.interceptor.HandlerInterceptor2"</span><span style="color: #0000ff">></</span><span style="color: #800000">bean</span><span style="color: #0000ff">></span>
        <span style="color: #0000ff"></</span><span style="color: #800000">mvc:interceptor</span><span style="color: #0000ff">></span>
    <span style="color: #0000ff"></</span><span style="color: #800000">mvc:interceptors</span><span style="color: #0000ff">></span>

3.Interception test

3.1 Testing requirements

Test the execution timing of each method of multiple interceptors.

3.2Write two interceptors

3.3 Both interceptors are allowed

Run log information:

<span style="color: #000000">HandlerInterceptor1...preHandle
HandlerInterceptor2...preHandle

HandlerInterceptor2...postHandle
HandlerInterceptor1...postHandle

HandlerInterceptor2...afterCompletion
HandlerInterceptor1...afterCompletion</span>

Summarize:

The preHandle method is executed in order, and postHandle and afterCompletion are executed in the reverse order of the interceptor configuration.

3.4 Interceptor 1 is allowed, Interceptor 2 is not allowed

Run log information:

<span style="color: #000000">HandlerInterceptor1...preHandle
HandlerInterceptor2...preHandle
HandlerInterceptor1...afterCompletion</span>

Summarize:

Interceptor 1 is released, and the preHandle of interceptor 2 will be executed.

The preHandle of interceptor 2 will not be released, and the postHandle and afterCompletion of interceptor 2 will not be executed.

As long as there is an interceptor that does not release, postHandle will not be executed.

3.5 Interceptor 1 is not allowed, Interceptor 2 is not allowed

Run log information:

HandlerInterceptor1...preHandle

The preHandle of interceptor 1 is not released, and postHandle and afterCompletion will not be executed.

The preHandle of interceptor 1 is not released, and interceptor 2 is not executed.

4. Summary

Apply the interceptor based on the test results.

For example: Unified log processing interceptor, if the interceptor preHandle needs to be changed, it must be released and placed at the first position in the interceptor chain.

For example: login authentication interceptor, placed at the first position in the interceptor chain. The permission verification interceptor is placed after the login interceptor. (Because the permissions are verified after the login is passed)

5.Interceptor application (implementing login authentication)

5.1 Requirements

(1) User request url

(2) Interceptor performs interception verification

If the requested URL is a public address (a URL that can be accessed without logging in), let it pass

If the user session does not exist, jump to the login page.

If the user session exists, release it and continue the operation.

5.2 Login and exit controller methods

<span style="color: #0000ff">package</span><span style="color: #000000"> joanna.yan.ssm.controller;

</span><span style="color: #0000ff">import</span><span style="color: #000000"> javax.servlet.http.HttpSession;
</span><span style="color: #0000ff">import</span><span style="color: #000000"> org.springframework.stereotype.Controller;
</span><span style="color: #0000ff">import</span><span style="color: #000000"> org.springframework.web.bind.annotation.RequestMapping;

@Controller
</span><span style="color: #0000ff">public</span> <span style="color: #0000ff">class</span><span style="color: #000000"> LoginController {
    
    </span><span style="color: #008000">//</span><span style="color: #008000">登录</span>
    @RequestMapping("/login"<span style="color: #000000">)
    </span><span style="color: #0000ff">public</span> String login(HttpSession session, String username, String password) <span style="color: #0000ff">throws</span><span style="color: #000000"> Exception{
        </span><span style="color: #008000">//</span><span style="color: #008000">调用service进行用户身份认证
        </span><span style="color: #008000">//</span><span style="color: #008000">...
        
        </span><span style="color: #008000">//</span><span style="color: #008000">在session中保存用户身份信息</span>
        session.setAttribute("username"<span style="color: #000000">, username);
        </span><span style="color: #0000ff">return</span> "redirect:items/queryItems.action"<span style="color: #000000">;
    }
    
    </span><span style="color: #008000">//</span><span style="color: #008000">退出</span>
    @RequestMapping("/logout"<span style="color: #000000">)
    </span><span style="color: #0000ff">public</span> String logout(HttpSession session) <span style="color: #0000ff">throws</span><span style="color: #000000"> Exception{
        </span><span style="color: #008000">//</span><span style="color: #008000">清除session</span>
<span style="color: #000000">        session.invalidate();
        </span><span style="color: #0000ff">return</span> "redirect:items/queryItems.action"<span style="color: #000000">;
    }
    
}</span>

5.3 Login authentication interception implementation

5.3.1LoginInterceptor

<span style="color: #0000ff">public</span> <span style="color: #0000ff">class</span> LoginInterceptor <span style="color: #0000ff">implements</span><span style="color: #000000"> HandlerInterceptor{

    </span><span style="color: #008000">//</span><span style="color: #008000">执行Handler完成执行此方法
    </span><span style="color: #008000">//</span><span style="color: #008000">应用场景:统一异常处理,统一日志处理</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">void</span><span style="color: #000000"> afterCompletion(HttpServletRequest request,
            HttpServletResponse response, Object handler, Exception ex)
            </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......afterCompletion"<span style="color: #000000">);
    }

    </span><span style="color: #008000">//</span><span style="color: #008000">进入Handler方法之后,返回modelAndView之前执行
    </span><span style="color: #008000">//</span><span style="color: #008000">应用场景从modelAndView出发:将公用的模型数据(比如菜单导航)在这里传到视图,也可以在这里同意指定视图</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">void</span><span style="color: #000000"> postHandle(HttpServletRequest request, HttpServletResponse response,
            Object handler, ModelAndView modelAndView) </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......postHandle"<span style="color: #000000">);
    }

    </span><span style="color: #008000">//</span><span style="color: #008000">进入Handler方法之前执行
    </span><span style="color: #008000">//</span><span style="color: #008000">用于身份认证、身份授权
    </span><span style="color: #008000">//</span><span style="color: #008000">比如身份认证,如果认证不通过表示当前用户没有登录,需要此方法拦截不再向下执行。</span>
<span style="color: #000000">    @Override
    </span><span style="color: #0000ff">public</span> <span style="color: #0000ff">boolean</span><span style="color: #000000"> preHandle(HttpServletRequest request, HttpServletResponse response,
            Object handler) </span><span style="color: #0000ff">throws</span><span style="color: #000000"> Exception {
        System.out.println(</span>"HandlerInterceptor1......preHandle"<span style="color: #000000">);
        </span><span style="color: #008000">//</span><span style="color: #008000">获取请求的url</span>
        String url=<span style="color: #000000">request.getRequestURI();
        </span><span style="color: #008000">//</span><span style="color: #008000">判断url是否是公开地址(实际使用时要将公开地址配置到文件中)
        </span><span style="color: #008000">//</span><span style="color: #008000">这里公开地址是登录提交的地址</span>
        <span style="color: #0000ff">if</span>(url.indexOf("login.action")>=0<span style="color: #000000">){
            </span><span style="color: #008000">//</span><span style="color: #008000">如果进行登录提交,放行</span>
            <span style="color: #0000ff">return</span> <span style="color: #0000ff">true</span><span style="color: #000000">;
        }
        </span><span style="color: #008000">//</span><span style="color: #008000">判断session</span>
        HttpSession session=<span style="color: #000000">request.getSession();
        String username</span>=(String) session.getAttribute("username"<span style="color: #000000">);
        </span><span style="color: #0000ff">if</span>(username!=<span style="color: #0000ff">null</span><span style="color: #000000">){
            </span><span style="color: #008000">//</span><span style="color: #008000">身份存在,放行</span>
            <span style="color: #0000ff">return</span> <span style="color: #0000ff">true</span><span style="color: #000000">;
        }
        
        </span><span style="color: #008000">//</span><span style="color: #008000">执行到这里,表示用户身份需要认证,跳转登录页面</span>
        request.getRequestDispatcher("/WEB-INF/jsp/login.jsp"<span style="color: #000000">).forward(request, response);
        
        </span><span style="color: #008000">//</span><span style="color: #008000">return false表示拦截,不向下执行
        </span><span style="color: #008000">//</span><span style="color: #008000">return true表示放行</span>
        <span style="color: #0000ff">return</span> <span style="color: #0000ff">false</span><span style="color: #000000">;
    }

}</span>

5.3.2 Interceptor configuration

Configuration in springmvc.xml under classpath:

If this article is helpful to you, please tip me on WeChat~

The above is the detailed content of Spring+SpringMVC+MyBatis in-depth learning and construction (17) - SpringMVC interceptor. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn