目录
1.简介
2.生成和校验
3.登录-生成令牌
4.过滤器Filter
快速入门
Filter执行流程
Filter拦截路径
过滤器链
登录校验Filter
流程
代码
5.拦截器Interceptor
快速入门
Interceptor拦截路径
执行流程
代码
继笔记04-session cookie
1.简介
2.生成和校验
/*
* 测试JWT令牌生成
* */
@Test
public void testGenJwt(){
Map<String,Object> claims = new HashMap<>();
claims.put("id",1);
claims.put("name","tom");
String jwt = Jwts.builder()
.signWith(SignatureAlgorithm.HS256,"mikey")//设置签名算法
.setClaims(claims)//自定义内容(载荷)
.setExpiration(new Date(System.currentTimeMillis()+3600*1000))//设置jwt令牌的有效期为1个小时
.compact();//拿到字符串类型的返回值
System.out.println(jwt);
}
/*
* 解析Jwt令牌
* */
@Test
public void testParseJwt(){
Claims claims = Jwts.parser()
.setSigningKey("mikey")
.parseClaimsJws("eyJhbGciOiJIUzI1NiJ9.eyJuYW1lIjoidG9tIiwiaWQiOjEsImV4cCI6MTcyMzA0MjYxNH0.OXLa75G0jGPDwNz95sUurab16UWY-5ZEMjWbOncfqJM")
.getBody();
System.out.println(claims);
}
3.登录-生成令牌
工具类:
package com.mikey.utils;
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 = "mikey";
private static Long expire = 43200000L;
/**
* 生成JWT令牌
* @param claims JWT第二部分负载 payload 中存储的内容
* @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;
}
}
Controller类:
package com.mikey.controller;
import com.mikey.pojo.Emp;
import com.mikey.pojo.Result;
import com.mikey.service.EmpService;
import com.mikey.utils.JwtUtils;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;
import java.util.HashMap;
import java.util.Map;
@Slf4j
@RestController
public class LoginController {
@Autowired
private EmpService empService;
@PostMapping("/login")
public Result login(@RequestBody Emp emp){
log.info("员工登录:{}",emp);
Emp e = empService.login(emp);
//登陆成功 生成令牌并且下发令牌
if(e!=null){
Map<String, Object> claims = new HashMap<>();
claims.put("id",e.getId());
claims.put("name",e.getName());
claims.put("username",e.getUsername());
String jwt = JwtUtils.generateJwt(claims);//jwt包含了当前登录的员工信息
return Result.success(jwt);
}
//登陆失败 返回错误信息
return Result.error("用户名或密码错误");
//return e!=null?Result.success():Result.error("用户名或密码错误");
}
}
4.过滤器Filter
快速入门
Filter执行流程
Filter拦截路径
过滤器链
登录校验Filter
流程
代码
package com.mikey.filter;
import com.alibaba.fastjson.JSONObject;
import com.mikey.pojo.Result;
import com.mikey.utils.JwtUtils;
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.springframework.util.StringUtils;
import java.io.IOException;
@Slf4j
@WebFilter(urlPatterns = "/*")
public class LoginCheckFilter implements Filter {
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
HttpServletRequest req = (HttpServletRequest) servletRequest;
HttpServletResponse resp = (HttpServletResponse) servletResponse;
//1.获取请求url
String url = req.getRequestURI().toString();
log.info("请求的url:{}",url);
//2.判断请求url中是否包含login,如果包含说明是登录操作,放行。
if(url.contains("login")){
log.info("登陆操作,放行");
filterChain.doFilter(servletRequest,servletResponse);
return;
}
//3.获取请求头中的令牌
String jwt = req.getHeader("token");
//4.判断令牌是否存在,如果不存在,则返回错误结果 未登录。
if(!StringUtils.hasLength(jwt)){
log.info("请求头taken为null,返回未登录的信息");
Result error = Result.error("NOT_LOGIN");
//手动转换 将对象转为json数据---》阿里巴巴fastJSON工具包 需要在pom文件中导入
String notLoginn = JSONObject.toJSONString(error);
resp.getWriter().write(notLoginn);
return;
}
//5.若jwt令牌存在 解析token,如果解析失败 返回错误结果 未登录
//快捷键alt crl t
try {
JwtUtils.parseJWT(jwt);
} catch (Exception e) {//jwt解析失败
e.printStackTrace();
log.info("解析令牌失败 返回未登陆的错误信息");
Result error = Result.error("NOT_LOGIN");
//手动转换 将对象转为json数据---》阿里巴巴fastJSON工具包
String notLoginn = JSONObject.toJSONString(error);
resp.getWriter().write(notLoginn);
return;
}
//6.放行
log.info("令牌合法 放行");
filterChain.doFilter(servletRequest,servletResponse);
}
}
5.拦截器Interceptor
快速入门
Interceptor拦截路径
执行流程
代码
package com.mikey.interceptor;
import com.alibaba.fastjson.JSONObject;
import com.mikey.pojo.Result;
import com.mikey.utils.JwtUtils;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
@Slf4j
@Component
public class LoginCheckInterceptor implements HandlerInterceptor {
@Override//目标资源方法运行前运行,返回true:放行 返回false 不放行
public boolean preHandle(HttpServletRequest req, HttpServletResponse resp, Object handler) throws Exception {
//1.获取请求url
String url = req.getRequestURI().toString();
log.info("请求的url:{}",url);
//2.判断请求url中是否包含login,如果包含说明是登录操作,放行。
if(url.contains("login")){
log.info("登陆操作,放行");
return true;//true代表放行 false代表不放行
}
//3.获取请求头中的令牌
String jwt = req.getHeader("token");
//4.判断令牌是否存在,如果不存在,则返回错误结果 未登录。
if(!StringUtils.hasLength(jwt)){
log.info("请求头taken为null,返回未登录的信息");
Result error = Result.error("NOT_LOGIN");
//手动转换 将对象转为json数据---》阿里巴巴fastJSON工具包
String notLoginn = JSONObject.toJSONString(error);
resp.getWriter().write(notLoginn);
return false;
}
//5.若jwt令牌存在 解析token,如果解析失败 返回错误结果 未登录
//快捷键alt crl t
try {
JwtUtils.parseJWT(jwt);
} catch (Exception e) {//jwt解析失败
e.printStackTrace();
log.info("解析令牌失败 返回未登陆的错误信息");
Result error = Result.error("NOT_LOGIN");
//手动转换 将对象转为json数据---》阿里巴巴fastJSON工具包
String notLoginn = JSONObject.toJSONString(error);
resp.getWriter().write(notLoginn);
return false;
}
//6.放行
log.info("令牌合法 放行");
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...");
}
}