登录校验一

登录校验

JWT令牌

  • 引入依赖

    XML 复制代码
    <!-- JWT依赖-->
    <dependency>
        <groupId>io.jsonwebtoken</groupId>
        <artifactId>jjwt</artifactId>
        <version>0.9.1</version>
    </dependency>

    在引入完JWT来赖后,就可以调用工具包中提供的API来完成JWT令牌的生成和校验。工具类:Jwts

  • 引入JWT工具类:在项目工程下创建 com.itheima.util 包,并把提供JWT工具类复制到该包下

    java 复制代码
    package com.itheima.util;
    
    import io.jsonwebtoken.Claims;
    import io.jsonwebtoken.Jwts;
    import io.jsonwebtoken.SignatureAlgorithm;
    
    import java.util.Date;
    import java.util.Map;
    
    public class JwtUtils {
    
        private static String signKey = "SVRIRUlNQQ==";
        private static Long expire = 43200000L;
    
        /**
         * 生成JWT令牌
         * @return
         */
        public static String generateJwt(Map<String,Object> claims){
            String jwt = Jwts.builder()
                    .addClaims(claims)
                    .signWith(SignatureAlgorithm.HS256, signKey)
                    .setExpiration(new Date(System.currentTimeMillis() + expire))
                    .compact();
            return jwt;
        }
    
        /**
         * 解析JWT令牌
         * @param jwt JWT令牌
         * @return JWT第二部分负载 payload 中存储的内容
         */
        public static Claims parseJWT(String jwt){
            Claims claims = Jwts.parser()
                    .setSigningKey(signKey)
                    .parseClaimsJws(jwt)
                    .getBody();
            return claims;
        }
    }
  • 完善 EmpServiceImpl中的 login 方法逻辑, 登录成功,生成JWT令牌并返回

    java 复制代码
    @Override
    public LoginInfo login(Emp emp) {
        Emp empLogin = empMapper.getUsernameAndPassword(emp);
        if(empLogin != null){
            //1. 生成JWT令牌
            Map<String,Object> dataMap = new HashMap<>();
            dataMap.put("id", empLogin.getId());
            dataMap.put("username", empLogin.getUsername());
            
            String jwt = JwtUtils.generateJwt(dataMap);
            LoginInfo loginInfo = new LoginInfo(empLogin.getId(), empLogin.getUsername(), empLogin.getName(), jwt);
            return loginInfo;
        }
        return null;
    }

过滤器Filter

过滤器的基本使用操作:

  • 第1步,定义过滤器 :1.定义一个类,实现 Filter 接口,并重写其所有方法。

  • 第2步,配置过滤器:Filter类上加 @WebFilter 注解 ,配置拦截资源的路径(指定属性urlPatterns)引导类上加 @ServletComponentScan 开启Servlet组件支持。

    拦截路径:

    |--------|--------------|-----------------------|
    | 拦截路径 | urlPatterns值 | 含义 |
    | 拦截具体路径 | /login | 只有访问 /login 路径时,才会被拦截 |
    | 目录拦截 | /emps/* | 访问/emps下的所有资源,都会被拦截 |
    | 拦截所有 | /* | 访问所有资源,都会被拦截 |

org.example.filter 包下创建TokenFilter:

java 复制代码
package org.example.filter;

import jakarta.servlet.*;
import jakarta.servlet.annotation.WebFilter;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.example.utils.JwtUtils;

import java.io.IOException;

@Slf4j
@WebFilter(urlPatterns = "/*")
public class TokenFilter implements Filter {
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;

        //1、获取请求路径
        String requestURI = request.getRequestURI();

        //2、判断是否是登录请求(login)放行
        if(requestURI.contains("/login")){
            log.info("登录请求,放行");
            filterChain.doFilter(request,response);
            return;
        }

        //3、获取请求头token
        String token = request.getHeader("token");

        //4、判断token是否存在,如果不存在说明没有用户登录,返回错误信息(响应401状态码)
        if(token == null || token.isEmpty()){
            log.info("令牌为空,响应401");
            response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
            return;
        }

        //5、如果token存在,校验令牌,如果校验失败,返回错误信息(响应401状态码)
        try{
            JwtUtils.parseJWT(token);
        }catch (Exception e){
            log.info("令牌非法,响应401");
            response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
            return;
        }

        //6、校验通过,放行
        log.info("令牌合法,放行");
        filterChain.doFilter(request,response);
    }
}

过滤器链上过滤器的执行顺序:注解配置的Filter,优先级是按照过滤器类名(字符串)的自然排序。 比如:

  • AbcFilter

  • DemoFilter

这两个过滤器来说,AbcFilter 会先执行,DemoFilter会后执行。

相关推荐
长三角活动观察1 分钟前
苏州独石传媒项目SOP拆解:从苏州智博会到出海大会,千人级活动的流程管控方法论
大数据·人工智能·传媒
01_ice2 分钟前
MySQL基本查询1
数据库·mysql
xieliyu.15 分钟前
UPD协议结构以及开发中注意事项
java·开发语言·笔记·java-ee
张宇Joaquin18 分钟前
openEuler编译和更换内核的方法
java·linux·服务器
程序员黑豆25 分钟前
Java正则表达式详解
java·前端·ai编程
腾科IT教育27 分钟前
Oracle OCP/OCM认证含金量实测2026版
数据库·oracle·ocp·ocm·甲骨文
Flynt1 小时前
我试了Spring Boot 4的原生镜像,聊聊那些数字和坑
java·spring boot
M-Robots echo8 小时前
轻量化裁剪方案解析:M-Robots 模块化构建,适配高低端各类机器人硬件平台
java·机器人·ros·开源社区·atomgit·m-robots
电商API_180079052479 小时前
京东商品详情API技术文章
大数据·运维·人工智能·网络爬虫
不可求~9 小时前
多模型路由怎么落地:把任务分流写进项目的最小实现
java·前端·数据库