session与JWT认证

本文探讨了在无状态协议下如何通过session管理和JWT来确保请求来源的识别,介绍了session的工作原理、存在的问题及解决方案,重点讲解了SSO(Single Sign-On)在多系统登录中的应用,包括CAS实现和JWT在认证中的优势与挑战。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一 、 问题原因:
http是无状态协议,用户每次访问,服务器都是新建会话,不能确定哪些请求是同一个用户发出的。

怎么确定请求来自同一个客户?

二、 session:

2.1 session是一种保存上下文信息的机制,且保存在服务端中,主要以cookie或者URL重写实现的

系统创造一个JSESSIONID的变量传输到cookie中, JSESSIONID保存在内存中,不写入硬盘

如果禁用浏览器cookie,服务器会改用URL重写传递Sessioid, Url中会存在sessionid=xxx字符串

JSESSIONID 不能跨窗口

2.2 服务端session
步骤:
1、用户向服务器发送用户名和密码。

2、服务器验证通过后,在当前对话(session)里面保存相关数据,比如用户角色、登录时间等等。

3、服务器向用户返回一个 session_id,写入用户的 Cookie。

4、用户随后的每一次请求,都会通过 Cookie,将 session_id 传回服务器。

5、服务器收到 session_id,找到前期保存的数据,由此得知用户的身份。

session在服务端,以散列表形式保存在内存中

2.3 session存在问题:
集群/多服务器 环境下,session不能共享

解决思路:
session复制到各个服务器 – 成本高,难维护,登录延迟
session集中存储 – 单独服务器管理,一般使用redis集中管理
使用JWT,服务器端不保存session

3 多服务下登录问题,SSO方案

大企业会有不同的系统,进入每个系统需要登录,获取session,访问对应资源

如何实现一次登录,可以进入不同系统

单点登录思路: 一个ticket进行串接各系统用户信息

外部session存储方案已经非常成熟了(比如Redis)

3.1 SSO
CAS实现单点登录
不同域名下 cookie无法跨域名共享,所以需要一个专门登录的域名(ouath.com)提供所有系统的sessionId
步骤:

  1. 当b.com 打开,发现未登录, 跳转到 ouath.com
  2. ouath.com 页面下输入账号密码登录
  3. ouath.com登录成功, cookie保存在ouath.com域名下
  4. sessionid放redis, 存放<ticket,sessionid>, 携带ticket重定向到b.com
  5. b.com重新打开,有一个ticket值
  6. b.com使用ticket到redis查询到sessionid, 并同步session,获取cookie,页面原地重定向
  7. b.com打开了页面,而且存了cookie

集中session管理优点:兼容旧版系统

三、JWT
JSON WEB Token(JWT,读作 [/dʒɒt/])
1、JWT原理:
用户登录后,生成一个对象,为了保证没有被篡改, 使用secret生成签名
token 包括 3部分

token = Header . Payload . Signature

1.1 Header(头部)
是一个JSON对象,描述了JWT元数据

{
  "alg": "HS256",  // 签名算法 默认是 HMAC SHA256
  "typ": "JWT"  // 类型
}

然后将该对象Base64URL编码成字符串

1.2 Payload(负载)
是一个JSON对象,存放要传递的数据,包括7个官方字段,可选用

iss (issuer):签发人
exp (expiration time):过期时间
sub (subject):主题
aud (audience):受众
nbf (Not Before):生效时间
iat (Issued At):签发时间
jti (JWT ID):编号

另外还可以自定义私有字段

由于JWT默认是不加密的,所有人可解码,不可以放秘密信息

该对象Base64URL编码成字符串

1.3 Signature (签名)
对前两个字串签名,防止被篡改.

服务端需要有一个密钥(sercret),使用Header里面的的签名算法, 生成签名

HMACSHA256(base64UrlEncode(header) + "." + HMACSHA256(base64UrlEncode(payload), secret)

最后使用点号分割三个部分,返回给用户

1.4 Base64URL编码
某些场合下会放到URL下, + / = 符号需要特使转义

2、 JWT使用流程
客户端接收到JWT,可以存在cookie,也可以存在localStorage中

每次与服务器通信,带上JWT, 在头部信息Authorization字段中
Authorization: Bearer <token>

跨域的时候可以把token放到post请求体中

3、JWT特点
3.1 默认不加密,不加密时不可把重要信息写在payload中
3.2 可以用于认证,也可以用于交换信息,减少了数据库查询次数
3.3 最大缺点, 服务器不报错session状态,不能废止或修改某个token, 在到期之前会有效,除非服务器使用token 黑名单记录token
3.4 JWT 包含认证信息,为减少盗用,有效期要设置比较短, 重要权限,需要再次认证
3.5 为减少盗用, 使用HTTPS协议传输
3.6 相比于Cookie, 占用空间更加大

3.7 安全性:
把重要信息存在localStorage是不安全的
如果您的站点包含来自域外源的第三方 JavaScript 代码,例如一些第三方脚本库的CDN源:
bootstrap 源
jQuery
广告脚本
谷歌分析链接
跟踪脚本

这些代码可以读取localStorage

存储在 HttpOnly Cookie
如果HTTP响应标头中包含HttpOnly标志(可选),客户端脚本将无法访问cookie;如果浏览器不支持HttpOnly,并且后端服务器尝试设置HttpOnly cookie,浏览器也会忽略HttpOnly标志,从而创建传统的,脚本可访问的cookie。那么该cookie(通常是会话cookie)容易受到XSS攻击

Cookie 的 HttpOnly 标签是防御 XSS 的解决方案之一,因为 HttpOnly 在简单的条件下阻止客户端(JavaScript)访问 Cookie。如果再将 secure 标志设置为 true,则只会在安全或加密的网络中使用 Cookie,从而增加其安全性。在使用这个方案的时候需要注意 JWT 的大小。如果 JWT 超过了 4KB 就不适合使用 Cookie 存储 JWT的方案。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值