登录鉴权方案中,session、token、cookie三者的区别及选择

前言

目前web常用的登录鉴权方案主要有3种,分别是session、token、cookie,每种方案都有其特定应用场景和局限性,本文主要针对几种方案的使用特点简单做一个对比分析。

阅读本文,首先需要对以上三者的概念和基本原理有基础了解,如不然,建议先详细了解一下上述三种方案的实现原理。

另除了上述三种方案外,localStroage作为前端的存储方式之一,实际可以简单理解为一个小型前端key-value数据库,由于不直接参与前后端交互且不影响登录鉴权,不在本文讨论范围内。

本质对比

  1. cookie:本质是一种本地local存储。
  2. session:本质是一种服务端server存储
  3. token:本质是一种无状态鉴权凭证,本地和服务端都不存储数据。但是现有的jwt方案允许在凭证里面,放一些简单数据。如jjwt的payload等

实现原理

  1. cookie方案:就是通过本地存储方式实现数据存储,没有什么讲的,唯一要注意的一点是cookie在http中是明文传输的,被抓包很轻易就可以拿到内部存储数据,所以I一般不会存储敏感信息。
  2. session方案:session的数据是放在server端的,但是为了使client传输的数据,server能认出来,所以本地还是要存储一个session id作为特定标识,用于server端识别session。这个session id会存储在cookie中,每次client端request都会携带,server端收到request后,根据session id获取server端存储的数据。
  3. token方案:是一种鉴权方案。client端发送账号密码到server端后,server端会根据用户信息生成一个新的凭证,即token,再将其发送给client端,以后client请求就不需要携带账号密码了,只需要携带这个token就可以完成用户身份识别。关于token的生成,目前业界有很多生成工具,比如jwt,其具体实现说的比较多,就不赘述了,可以看下这篇文章

各自特点

  1. cookie本地存储
    优势:节省server端性能及空间
    劣势:本地存储数据有泄漏风险

  2. session服务端存储
    优势:数据安全性好相对cookie有提升
    劣势:消耗server端性能及空间,

  3. token
    优势:无状态,server端不保存任何token信息
    缺点:由于severt端可以不保存token数据信息,因此无法强制控制token的失效,只能通过自然过期进行实效控制

session的其他问题

我们可以看到,session的主要特点首先与cookie特点相反。但是在此之外,由于session默认是基于单体server生成的,也带来了其他的问题,如:当server端宕机的时候,其内部的数据会清空,所以导致session数据丢失等问题,这些问题,可以通过spring session(通过redis存储session信息)等分布式session手段解决。

登录鉴权方案的选择

前提

在登录鉴权的过程中,我们需要先达成几个共识。

  1. 登录鉴权的过程中,不能让用户换一个页面就输入一次账号密码,因此一定要有自动登录机制,这是登录鉴权机制存在的意义。
  2. 登录鉴权的过程中,最主要的是解决安全问题,其次才是考虑性能等其他问题。

因此我们优先分析安全问题

安全问题

首先,我们看一下在实现自动登录机制的过程中,三种方案在前后端数据交互的过程中传递的是什么。

  1. cookie:传递的是账号密码,明文传输
  2. session:传递的是session id,放在cookie中明文传输
  3. token:传递的是token值,一般放在header中明文传输,在token内部完成加密

我们可以看到

① 如果使用cookie方案,hacker在拿到账号密码后,在无限期内,都可以任意请求server端数据。
② 如果使用session方案或token方案,即便hacker拿到了明文传输的session id或token,可以任意请求server端数据,但是可以通过session强制刷新以及token过期机制,控制其破坏时长。

可以注意到一个问题,就是目前登录过程中,是没有绝对安全的方案的。即便是每次都输入账号密码,然后对传输内容加密,也会存在hacker劫持加密后数据,伪造登录的可能。但我们希望你hacker劫持,也不要劫持一个永久的值,因此最好的方法只能尽量减少账号密码的使用,token和session的存在恰好解决了此问题。

所以自动登录方案首先排除cookie方案,剩下的session和token方案可以用于登录鉴权,从理论上来讲,session方案和token方案是可以将安全性能力做到一致的。(当然可以基于加密算法在cookie的基础上实现加密传输,但是这种方案就类似于token方案了,在此不讨论)

适用场景

token与session的不同点

解决了安全问题,此时候选方案只有两个了,session和token,那么这两者该怎么选呢?

前面提到,client端每次请求都需要携带一个数据(token与session id)发送到server端,那两者的区别在哪儿呢?为什么有了session id 的情况下,还要搞出个token来呢?
首先我们要分清楚,什么是token,什么是session id。

  1. session id可以认为是是一个key,server相当于是一个大hash map,本质上使用使用session id的过程,就是从map取value的过程。所以无论使用分布式session还是单体session,本质上都是一种中心化方案。

  2. token本质上是用户凭证。可以认为是为用户换了套账号密码。只有在client第一次login的时候,采用自定义的账号密码,login成功后,server端会发送一套新的认证凭证给你,每次请求的时候自动携带,就代替了账号密码的作用。这样做有几个好处

    • 首先是不用手动输入账号密码了,因为在request的时候,header里面就自带了。
    • 其次是用的是server端新发的凭证,即便泄漏了,也不会导致用户自定义的账号密码泄漏。
    • 最重要的一点,server端可以不记录token凭证,只需要有加密的秘钥和算法通过验证的方式,就能识别用户的身份了,不用挨个去数据库比对。

    当然在颁发凭证的时候,sever端也可以放一些其他信息(如jjwt的payload字段),但是这些信息相当于是明文的(base64加密可逆),本身没有保密要求,所以不存在安全问题。
    这就使得token很容易做成去中心化方案,因为数据不需要存储,就不需要集中

三种方案在登录场景中适用总结

首先,所有等登录方案,做多点登录都是最容易的,做单点登录要在多点登录的基础上,存储登录数据,做唯一性校验。
因而,以上三种方案在登录场景中,

  1. cookie:不能用,因为安全问题否决。
  2. session:中心化方案,实现多点登录没问题,由于做了中心化数据存储,做数据唯一性校验问题也不大,所以单点登录也没问题。
  3. token:去中心化方案,天生适合多点登录,不适合做单点登录。原因在于,没有中心化数据存储登录信息,无法完成唯一性校验。

当然如果硬要用token做单点登录,可以考虑分布式场景下,多节点token数据同步方案,或者单独搞一个集中式数据存储(如redis等)存储登录信息。但是这种方案,其实就趋同于session方案了,所以还不如直接用session。
另外,集中式数据存储的一个天然缺陷就是一定会存在IO瓶颈,而去中心化方案,在大并发,分布式场景下,具有重要的实践意义。所以token+多点登录更适合于高并发场景下的登录设计。

  • 14
    点赞
  • 33
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值