RESTful API使用JWT做无状态的身份认证

xiaoxiao2021-02-28  37

JWT设计

RESTful架构的前后端,经常会使用Token令牌做身份验证,JWT(JSON Web Token)是一种简单易用的Token标准,适合在应用中做无状态的API身份认证。

jwt由Header、Payload、Signature三部分组成,使用 . 分割开,一个JWT形式:

Header.Payload.Signature

这三部分分别对应的是加密算法、携带的用户信息、加密后的字符串(签名)。

Jwt自带签名,能够防止伪造或篡改,但要防止token被窃取还要配合https使用。

下面我们用Jwt开发一个前后端交互系统。

JWT服务端

这里使用jjwt开源库生成token:

https://github.com/jwtk/jjwt

创建RESTful接口

Server端基于SpringBoot开发,提供生成token和校验token的接口:

@PostMapping("/login") Back login(@RequestParam String name, @RequestParam String pwd); @GetMapping("/user") Back getUser(@RequestHeader String jwt);

登录或注册接口:客户端提交用户名密码,服务端完成登录或注册逻辑,然后生成jwt令牌并返回给客户端

用户信息接口:客户端将token放在请求头,服务端校验是否合法,然后再从MySQL中查询并返回用户信息

服务端无需存储jwt令牌,通过特定的算法和密钥校验token,同时取出Payload中携带的用户ID,减少不必要的数据库查询

本例中设置JWT有效期为3天,服务端每次都会自动校验token是否过期,如果过期就直接抛出异常,客户端需要重新申请token

Token统一校验

业务相关接口一般都需要token验证,这就应该把验证逻辑放在一个统一的切面层完成,Spring的AOP正好满足这一需要。

这里实现Spring的拦截器HandlerInterceptor接口,在Controller方法执行之前拦截需要鉴权的请求,验证token是否合法,合法就放行,不合法则直接抛出异常拦截请求。

public class JwtInterceptor implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) { //在请求处理之前校验token String token = httpServletRequest.getHeader("jwt"); return Util.verify(token); } @Override public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) { } @Override public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) { } }

然后在WebMvcConfigurerAdapter中添加此拦截器,就可以实现Token统一校验了。

服务端源码:https://github.com/yunTerry/JWT-Server

JWT客户端

Android客户端使用Retrofit做REST请求。

登录或注册接口:提交用户名密码,服务端返回jwt令牌:

用户信息接口:客户端将token放在请求头,服务端校验通过即返回用户信息

客户端在本地存储token以后就能免登陆

客户端源码:https://github.com/yunTerry/JWT-Android

JWT的缺陷

JWT使用起来虽然简单方便,但它存在一个缺陷,即服务端无法主动注销token,如果修改秘钥会让所有token失效,代价太大,通常只是被动等待token过期失效,所以jwt在安全性上不及session,实际开发中应合理设置过期时间。

如果要让服务端能够注销token,就要在服务端维护token状态,但这又回到session机制了。

JWT这个缺陷决定了它更适合用在短期的token验证场景中,或者也可以结合session做长短期双重验证,弥补session的一些不足。

转载请注明原文地址: https://www.6miu.com/read-800124.html

最新回复(0)