首页 > 其他分享 >过滤器

过滤器

时间:2022-10-21 16:34:38浏览次数:33  
标签:return String request response 过滤器 import public

过滤器实现过程:

答题实现步骤:

  1. 编写**Fiter.java 实现Filter接口
  2. 在启动项添加注解 @ServletComponentScan

Filter 配置编写

@Slf4j
@WebFilter(filterName = "LoginCheckFilter" ,urlPatterns = "/*")
public class LoginCheckFilter implements Filter {

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;
    	
        // 被拦截的 uri
        String uri = request.getRequestURI();
     	log.info("拦截该请求 {}",request.getRequestURI());
        
        // 进行拦截后的处理逻辑
        
        //释放拦截
         filterChain.doFilter(request, response);
    }

详解

Filter 使用方法:

暂时记录两种实现方法,具体细节简单测了一下,以后学了注解之类的只是在进行细节分析

  • 使用@WebFilter注解,指定拦截路径一些参数,但是无法确定优先级。同时需要在启动类,使用@ServletComponentScan扫描带@WebFilter、@WebServlet、@WebListener并将其注入bean中。
  • 通过@FilterRegistrationBean 实例注册实现

@WebFilter + @ServletComponentScan

@Slf4j
@WebFilter(filterName = "LoginCheckFilter" ,urlPatterns = "/*")
public class LoginCheckFilter implements Filter {

    public static final AntPathMatcher PATH_MATCHER = new AntPathMatcher();
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;
        log.info("拦截该请求 {}",request.getRequestURI());

        filterChain.doFilter(request, response);


        String uri = request.getRequestURI();
        // 至少登录界面不应该进行拦截, 写出不需要拦截的所有uri
        String[] freeUris = new String[]{
                "/employee/login",
                "/employee/logout",
                "/backend/**",
                "/front/**"
        };

        boolean check = cheak(uri, freeUris);

        if (check) {
            log.info("自由权限网页");
            filterChain.doFilter(request, response);
            return;
        }

        // 判断登录状态,若一登陆,则直接释放
        if (request.getSession().getAttribute("employee") != null) {
            log.info("用户已登录");
            filterChain.doFilter(request, response);
            return;
        }


        response.getWriter().write(JSON.toJSONString(R.error("NOTLOGIN")));
        log.info("跳转ing....");
        return;


    }

    public boolean cheak(String uri, String[] freeUris) {
        for (String u : freeUris ) {
            if (PATH_MATCHER.match(u,uri)) {
                return true;
            }
        }
        return false;
    }
}

在启动类上 添加@ServletComponentScan注解。

如果忘记添加这个注解。就没有将我们编写的过滤器注入spring管理的bean中. 整个程序的没有产生任何拦截 出现任何效果.

@FilterRegistrationBean

package com.itheima.reggie.filter;

import com.alibaba.fastjson.JSON;
import com.itheima.reggie.common.R;
import com.sun.javafx.webkit.CursorManagerImpl;
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.stereotype.Component;
import org.springframework.util.AntPathMatcher;

import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * @author serendipity
 * @version 1.0
 * @date 2022/10/21 15:13
 **/
@Slf4j
// @WebFilter(filterName = "LoginCheckFilter" ,urlPatterns = "/*")
public class LoginCheckFilter implements Filter {
    public static final AntPathMatcher PATH_MATCHER = new AntPathMatcher();
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;
        log.info("拦截该请求 {}",request.getRequestURI());




        String uri = request.getRequestURI();
        // 至少登录界面不应该进行拦截, 写出不需要拦截的所有uri
        String[] freeUris = new String[]{
                "/employee/login",
                "/employee/logout",
                "/backend/**",
                "/front/**"
        };

        boolean check = check(freeUris,uri);

        if (check) {
            log.info("自由权限网页");
            filterChain.doFilter(request, response);
            return;
        }

        // 判断登录状态,若一登陆,则直接释放
        if (request.getSession().getAttribute("employee") != null) {
            log.info("用户已登录");
            filterChain.doFilter(request, response);
            return;
        }


        response.getWriter().write(JSON.toJSONString(R.error("NOTLOGIN")));
        log.info("跳转ing....");
        return;


    }

    public boolean check(String[] urls,String requestURI) {
        for (String url : urls) {
            boolean match = PATH_MATCHER.match(url, requestURI);
            if (match) {
                return true;
            }
        }
        return false;
    }
}
package com.itheima.reggie.filter;

import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @author serendipity
 * @version 1.0
 * @date 2022/10/21 16:05
 **/
@Configuration
public class FilterConfiguration {
    @Bean
    public FilterRegistrationBean<LoginCheckFilter> test(){
        FilterRegistrationBean<LoginCheckFilter> bean = new FilterRegistrationBean<>();
        bean.setFilter(new LoginCheckFilter()); // 注册自定义过滤器
        bean.setName("LoginCheckFilter");// 过滤器名称
        bean.addUrlPatterns("/*");// 过滤所有路径
        // bean.setOrder(1);// 设置优先级
        return bean;
    }
}

第二个与上面相比, 唯一的区别就是在实现Filter接口的类, 少了@WebFilter(filterName = "LoginCheckFilter" ,urlPatterns = "/*"), 启动类也没有了@ServletComponentScan 注解.

出现一个问题:

2022-10-21 16:20:01.595  WARN 32632 --- [io-8080-exec-10] .w.s.m.s.DefaultHandlerExceptionResolver : Failure while trying to resolve exception [org.springframework.http.converter.HttpMessageNotReadableException]

2022-10-21 16:20:01.597 ERROR 32632 --- [io-8080-exec-10] o.a.c.c.C.[.[.[/].[dispatcherServlet]    : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.http.converter.HttpMessageNotReadableException: I/O error while reading input message; nested exception is java.io.IOException: Stream closed] with root cause

这个warn 和 error 的话
注意是在filter实现类的代码逻辑处理过程中,将拦截释放掉了,但是后面没有使用return,结束后面的操作.
   filterChain.doFilter(request, response);

标签:return,String,request,response,过滤器,import,public
From: https://www.cnblogs.com/serendipity-igao/p/16813893.html

相关文章