Skip to content

深入理解 Session

一、为什么需要 Session?

Cookie 虽然能将数据保存在客户端,有效减轻服务器的存储压力,但它存在一个致命缺陷:安全性不足

由于 Cookie 存储在客户端,其中的数据可以被用户轻易获取和篡改。对于不敏感的数据,这没有问题。但对于像验证码、用户登录状态等敏感信息,如果直接存储在 Cookie 中,会带来严重的安全隐患。


二、案例分析:验证码的安全困境

验证码的核心目的是为了验证操作者是“人”而非“机器”,并确认用户的真实身份(如手机号)。

如果服务器在生成验证码后,直接通过 Cookie 将其发送给浏览器,会发生什么?

  • 流程

    1. 客户端(浏览器)向服务器请求发送验证码,并附上手机号。
    2. 服务器生成随机验证码(如 1036),通过短信发送给用户手机。
    3. [错误步骤] 服务器同时将验证码 1036 通过 Set-Cookie 响应头写入客户端的 Cookie 中。
    4. 用户输入收到的验证码并提交。
    5. 客户端 JS 或服务器通过比对用户输入的值和 Cookie 中的值来验证。
  • 安全漏洞: 攻击者根本不需要接收短信。他可以直接打开浏览器的开发者工具,在 Cookie 中查看到验证码的明文 1036。这使得验证码机制形同虚设,攻击者可以轻松绕过验证。

    这就好比猜谜游戏,出题人却把答案直接写在了你的脸上。

2. 正确的实现方式:使用 Session

Session 将敏感数据保留在服务器,只给客户端一个“凭证”,从而解决了安全问题。

  • 流程

    1. 客户端向服务器请求发送验证码,并附上手机号。
    2. 服务器生成随机验证码(如 1036),通过短信发送给用户手机。
    3. [关键步骤] 服务器在自身开辟一块内存或数据库空间(即 Session),将验证码存入。
      // 服务器端伪代码
      session.set('verify_code', '1036');
    4. 服务器生成一个独一无二的、与 1036 无任何关联的字符串,称为 Session ID (SID)
    5. 服务器通过 Set-Cookie 将这个 SID 发送给客户端。
    6. 用户输入收到的验证码 1036 并提交。
    7. 浏览器在提交请求时,会自动带上包含 SID 的 Cookie。
    8. 服务器接收到请求后: a. 通过请求中的 SID 找到对应的 Session 数据。 b. 从 Session 中取出之前存储的正确验证码 1036。 c. 与用户提交的验证码进行比对,完成验证。
  • 安全性: 客户端自始至终只持有一个无意义的 SID(好比一个保险柜的钥匙),而真正的验证码(保险柜里的贵重物品)安全地存放在服务器端。客户端无法通过钥匙直接看到里面的内容,从而保证了数据的安全。


特性CookieSession
存储位置客户端(浏览器)服务器端
安全性较低,数据暴露在客户端,易被窃取和篡改。较高,数据存储在服务器,客户端无法直接访问。
服务器压力减轻服务器存储压力。增加服务器存储和计算压力。
存储容量有限(通常单个 Cookie 为 4KB)。理论上无限(取决于服务器的内存或硬盘容量)。
数据类型只能是字符串可以是任意数据类型(如数字、对象等,取决于服务器端实现)。

四、面试核心:如何清除 Session?

Session 数据是临时的,如果不及时清理,会持续占用服务器资源。但服务器无法直接感知用户是否关闭了浏览器。因此,清理 Session 通常有两种策略:

1. 设置过期时间(被动清除)

这是最常用的方法。服务器为每个 Session 设置一个固定的“非活跃”时间,例如 20分钟

  • 机制:如果服务器在 20 分钟内没有收到任何携带该 Session ID 的请求,就认为用户已经离开,服务器会自动销毁该 Session 数据。
  • 优点:实现简单,可靠性高。

2. 客户端主动通知(主动清除)

通过前端技术,在用户关闭网页或标签页时,主动向服务器发送一个“下线”请求。

  • 机制:监听浏览器的 beforeunloadunload 事件,当事件触发时,通过 JavaScript 发送一个特定的请求通知服务器。服务器收到该请求后,立即销毁对应的 Session。
  • 缺点:存在不确定性,例如用户强制关闭浏览器、断电或网络中断时,该请求可能无法成功发出。

五、对前端开发者的意义

对于前端开发者而言,Session 的工作机制通常是透明的

  • 你不需要手动管理 Session ID,浏览器会自动处理该 Cookie 的存储和发送。
  • 你的工作是按照接口文档,在合适的时机(如登录、提交表单)向服务器发送请求。
  • 理解 Session 的原理有助于你更好地与后端工程师协作,并在出现问题时能快速定位是前端还是后端的原因。