Day21_学点儿JavaEE__过滤器Filter(登录验证、编码处理)

1 为什么要使用过滤器

昨天已经总结过

当然,这仅仅是完成了一个简单的登录过程,即完成判断输入信息是否和数据库信息相匹配的操作,但是仍然可以通过直接输入地址的方式,在不登录的情况下访问相应的页面。而我们实际生活中的没登录的情况下,很多页面是无法访问的,要实现这样的效果,我们可以在每个页面都增加一个判断Session中的用户名密码是否和数据库匹配的操作,但是未免也太麻烦了 点。通过过滤器Filter,可以很简单地实现这个效果

项目开发中,经常会用到重复代码的实现。

  1. 请求每个servlet都要设置编码
  2. 判断用户是否登录,只有登录了才有操作权限。

2 过滤器相关API

interface Filter 过滤器核心接口

  1. init(FilterConfig filterConfig)
    初始化方法,在服务器启动的时候就执行
  2. doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
    过滤器拦截的业务逻辑处理
  3. destroy()
    销毁过滤器实例的时候调用

interface FilterChain 过滤链

doFilter(ServletRequest request, ServletResponse response)

执行下一个过滤器或放行(访问servlet)

3 案例一:用过滤器完成登录

java 复制代码
// /*  拦截所有的请求
@WebFilter(filterName = "login", urlPatterns = "/*")
public class LoginFilter implements Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        Filter.super.init(filterConfig);
        System.out.println("LoginFilter.init");
    }

    // ServletRequest servletRequest = new HttpServletRequest()
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        System.out.println("LoginFilter.doFilter");
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;

        String servletPath = request.getServletPath();
        System.out.println("servletPath:" + servletPath);
        String method = request.getParameter("method");
        //这是请求是要去完成登录的,不需要执行后面验证是否登录的流程
        if (servletPath.endsWith(".jpg")
                || servletPath.endsWith(".png")
                || servletPath.endsWith(".js")
                || servletPath.endsWith(".css")
                || servletPath.equals("/login.jsp")
                || servletPath.equals("/user") && "login".equals(method)) {
            filterChain.doFilter(servletRequest, servletResponse);
            return;
        }

        HttpSession session = request.getSession();
        User user = (User) session.getAttribute("user");
        if (user == null) {
            response.sendRedirect("/login.jsp");
            return;
        }

        //加了这句话代表方行,继续往后执行,
        //如果还有filter就访问后面filter,没有filter,就可以访问后台资源
        filterChain.doFilter(servletRequest, servletResponse);
    }

    @Override
    public void destroy() {
        Filter.super.destroy();
        System.out.println("LoginFilter.destroy");
    }
}

4 案例二:用过滤器处理POST请求乱码问题

由于在案例一中的登录过滤器中调用了request.getParameter("method")方法,这会导致之前在其他Servlet中设置的request.setCharacterEncoding("UTF-8");处理乱码失效(因为Filter会先执行),所以我们可以再单独设置一个处理乱码的Filter。

java 复制代码
@WebFilter(filterName = "encoding", urlPatterns = "/*")
public class EncodingFilter implements Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {

    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        System.out.println("EncodingFilter.doFilter");
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        // 这个method是get还是post
        String method = request.getMethod();
        // 解决post请求乱码问题
        if ("post".equalsIgnoreCase(method)) {
            request.setCharacterEncoding("UTF-8");
        }

        filterChain.doFilter(servletRequest, servletResponse);
    }

    @Override
    public void destroy() {

    }
}

5 web.xml配置servlet和过滤器(多个Filter优先级)

servlet和filter除了用注解方式配置,还可以使用xml的方式配置

WEB-INF/web.xml是Web项目的核心配置文件

html 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">



    <!--
        @WebServlet("/student")
        public class StudentServlet extends HttpServlet { }
    -->              
    <servlet>
        <servlet-name>studentServlet</servlet-name>
        <servlet-class>com.situ.web.controller.StudentServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>studentServlet</servlet-name>
        <url-pattern>/student</url-pattern>
    </servlet-mapping>
    



    <filter>
        <filter-name>encoding</filter-name>
        <filter-class>com.situ.web.filter.EncodingFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>encoding</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <filter>
        <filter-name>login</filter-name>
        <filter-class>com.situ.web.filter.LoginFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>login</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
</web-app>

先设置的Filter优先级高于后设置下的Filter优先级。在web.xml配置servlet和Filter的话,要把@@WebServlet("/student")@WebFilter(filterName = "login", urlPatterns = "/*")注解形式的语句注释掉,不然会有冲突。

代码

Day20_复制粘贴快速开发(课程表)、CookieDemo、Filter登录过滤及放行、教师薪资显示0.0
Day21_过滤器处理POST乱码,JS DOM、点击事件,JQuery

相关推荐
llwszx2 小时前
深入理解Java锁原理(一):偏向锁的设计原理与性能优化
java·spring··偏向锁
云泽野3 小时前
【Java|集合类】list遍历的6种方式
java·python·list
二进制person3 小时前
Java SE--方法的使用
java·开发语言·算法
小阳拱白菜4 小时前
java异常学习
java
FrankYoou5 小时前
Jenkins 与 GitLab CI/CD 的核心对比
java·docker
麦兜*6 小时前
Spring Boot启动优化7板斧(延迟初始化、组件扫描精准打击、JVM参数调优):砍掉70%启动时间的魔鬼实践
java·jvm·spring boot·后端·spring·spring cloud·系统架构
KK溜了溜了6 小时前
JAVA-springboot 整合Redis
java·spring boot·redis
天河归来6 小时前
使用idea创建springboot单体项目
java·spring boot·intellij-idea
weixin_478689767 小时前
十大排序算法汇总
java·算法·排序算法
码荼7 小时前
学习开发之hashmap
java·python·学习·哈希算法·个人开发·小白学开发·不花钱不花时间crud