JWT鉴权 | 青训营笔记

55 阅读3分钟

这是我参与「第五届青训营 」伴学笔记创作活动的第17天

青训营项目接口给定的的token如何使用?一开始这是个很困扰我的问题。 在网上找了许多资料,从java的springsecurity的文章,学到了Go的jwt使用。

为什么我们要用token呢?

曾经我用java写项目的时候,判断登录逻辑直接使用session,虽然保证了安全性,但在用户多的时候,存储的数据量也不小。由于 session 保存在服务器端,它的安全性和灵活性都要比 token 差一些。

使用jwt实现用户鉴权的原理是什么呢?

用户发送数据给后端,后端使用数据经加密签名形成复杂的字符串,我们可以叫做令牌。然后服务器将这个令牌交给客户端,以后客户端每次访问就带上这个令牌,然后服务端检验是否有这个的存在或这个令牌是否过期,检验通过后才会让客户端进行访问。

我们可以使用handler来对token进行校验,并将需要的数据放入context上下文中,需要的时候取出。替代了之前使用的用线程保存参数,使得保存更加的稳定,也更加的安全。

token 与 session的优缺点

优点:

  • 可扩展性好

应用程序分布式部署的情况下,Session需要做多机数据共享,通常可以存在数据库或者Redis里面。而JWT不需要。

  • 无状态

JWT不在服务端存储任何状态。RESTful API的原则之一是无状态,发出请求时,总会返回带有参数的响应,不会产生附加影响。用户的认证状态引入这种附加影响,这破坏了这一原则。另外JWT的载荷中可以存储一些常用信息,用于交换信息,有效地使用 JWT,可以降低服务器查询数据库的次数。

缺点:

  • 安全性:由于JWT的payload是使用Base64编码的,并没有加密,因此JWT中不能存储敏感数据。而Session的信息是存在服务端的,相对来说更安全。

  • 性能:JWT太长。由于是无状态使用JWT,所有的数据都被放到JWT里,如果还要进行一些数据交换,那载荷会更大,经过编码之后导致JWT非常长,Cookie的限制大小一般是4k,cookie很可能放不下,所以JWT一般放在LocalStorage里面。并且用户在系统中的每一次Http请求都会把JWT携带在Header里面,Http请求的Header可能比Body还要大。而SessionId只是很短的一个字符串,因此使用JWT的Http请求比使用Session的开销大得多。

  • 一次性:无状态是JWT的特点,但也导致了这个问题,JWT是一次性的。想修改里面的内容,就必须签发一个新的JWT。即缺陷是一旦下发,服务后台无法拒绝携带该jwt的请求(如踢除用户)