对过滤器和拦截器的认识和总结

参考:http://blog.csdn.net/chenleixing/article/details/44573495
http://haohaoxuexi.iteye.com/blog/1750680

以前在学习时一直搞不清这两者的区别,以为过滤器是servlet中的,拦截器是springmvc的,后来在做一个登录拦截的时候,发现两者都可以实现,所以稍微的终结了一下。
下图是过滤器和拦截联合使用时的请求的流程

这里写图片描述

过滤器是JavaEE标准,采用函数回调的方式进行。是在请求进入容器之后,还未进入Servlet之前进行预处理,并且在请求结束返回给前端这之间进行后期处理。

拦截器是被包裹在过滤器之中的。

@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
    System.out.println("preHandle");
    return true;
}

@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
    System.out.println("postHandle");
}

@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
    System.out.println("afterCompletion");
}

  a.preHandle()这个方法是在过滤器的chain.doFilter(request, response)方法的前一步执行,也就是在 [System.out.println(“before…”)][chain.doFilter(request, response)]之间执行。
  b.preHandle()方法之后,在return ModelAndView之前进行,可以操控Controller的ModelAndView内容。
  c.afterCompletion()方法是在过滤器返回给前端前一步执行,也就是在[chain.doFilter(request, response)][System.out.println(“after…”)]之间执行。

下面是具体的使用方式
这里写图片描述

1.编写一个java类,实现Filter接口

package cn.note.web;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.context.ApplicationContext;
import org.springframework.web.context.support.WebApplicationContextUtils;

import cn.tedu.note.service.UserService;

public class ACLFilter implements Filter{

    private ServletContext sc;
    private ApplicationContext ctx;
    private UserService userService;

    /**
     * 过滤器初始化代码
     */
    public void init(FilterConfig cfg)
        throws ServletException {

        sc= cfg.getServletContext();
        //获取Spring容器
        ctx=WebApplicationContextUtils.getWebApplicationContext(sc);
        //从容器中获取 UserService 对象
        userService=ctx.getBean("userService",UserService.class);

    }
    public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)throws IOException, ServletException {
        chain.doFilter(request, response); 
    }
    public void destroy() {
    }
}

2.doFilter中实现拦截

public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)throws IOException, ServletException {
        HttpServletRequest request=(HttpServletRequest) req;
        HttpServletResponse response =(HttpServletResponse) res;

        String path=request.getRequestURI();
        //System.out.println(path);

        path = path.substring(
            path.indexOf('/', 1));

        //System.out.println("trim path:"+path);

        if(path.matches(".*/edit\\.html$")){
            checkLogin(request,response,chain);
            return;
        }

        if(path.matches(".(note).*\\.do$")){
            checkDotDo(request,response,chain);
            return;
        }

        chain.doFilter(request, response); 
    }

3.将过滤器添加到web程序中
在web.xml中添加如下的配置

<filter>
        <filter-name>acl</filter-name>
        <filter-class>
                cn.note.web.ACLFilter
        </filter-class>
    </filter>
    <filter-mapping>
        <filter-name>acl</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping> 

4.打包部署。。
这样一个简单的过滤器就已经完成了。其最核心的其实也就是dofilter里面对过滤条件的判断

下面是拦截器的使用
和过滤器一样
第一步:首先 implements HandlerInterceptor接口
第二步:由于我要在执行controller之前拿到cookie的value
所以我在preHandle方法里面实现代码
第三步:与spring的项目整合

package com.jt.web.interceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.jt.common.service.HttpClientService;
import com.jt.common.util.CookieUtils;
import com.jt.web.controller.UserController;
import com.jt.web.controller.UserThreadLocal;
import com.jt.web.pojo.User;


public class CartInterception implements HandlerInterceptor{
    @Autowired
    private HttpClientService httpClientService;

    private static final ObjectMapper MAPPER=new ObjectMapper();

    //在执行整个controller完成渲染之后(数据完成绑定后,即将就要转发了),转向页面之前
    @Override
    public void afterCompletion(HttpServletRequest arg0, HttpServletResponse arg1, Object arg2, Exception arg3)
            throws Exception {
        // TODO Auto-generated method stub

    }


    //在执行controller之后
    @Override
    public void postHandle(HttpServletRequest arg0, HttpServletResponse arg1, Object arg2, ModelAndView arg3)
            throws Exception {
        // TODO Auto-generated method stub

    }


    //在执行controller方法前执行
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse arg1, Object arg2) throws Exception {
        //从cookie中获取ticket
        String ticket=CookieUtils.getCookieValue(request, UserController.UsercookieName);
        if(StringUtils.isEmpty(ticket)){
            UserThreadLocal.setUser(null);

        }else{
            //成功获取ticket
            String url="http://sso.jt.com/user/query/"+ticket;

            String jsonData=httpClientService.doGet(url, "utf-8");
            if(StringUtils.isNoneEmpty(jsonData)){
                //成功获取jsonData
                JsonNode jsonNode=MAPPER.readTree(jsonData);
                String data=jsonNode.get("data").asText();

                User user=MAPPER.readValue(data, User.class);
                UserThreadLocal.setUser(user);
            }else{
                UserThreadLocal.setUser(null);
            }



        }

        return true;//默认不放行,日常的情况下,不管对错都放行
    }

}

在springmvc的配置文件中添加

<!-- 配置拦截器 -->
    <mvc:interceptors>
        <mvc:interceptor>
            <!-- 指定拦截的映射 ,**拦截后面的多级目录-->
            <mvc:mapping path="/cart/**"/>
            <!-- 指定实现类 -->
            <bean class="com.jt.web.interceptor.CartInterception"></bean>
        </mvc:interceptor>

    </mvc:interceptors>

发布部署即可。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值