登录一个网站,点个购物车,再跳到个人中心——这些操作背后,系统得知道“你是谁”。但怎么记住你?靠 session 还是 token?很多人一上来就翻文档、查框架,结果越看越晕。其实不用那么复杂,先搞清场景,再对号入座。
session 是什么?就像饭店的桌牌
你去小餐馆吃饭,老板给你发个号牌,写上“3号桌”,服务员凭这个号给你上菜、结账。session 就是这么个东西:服务端生成一个唯一 ID(比如 sess_abc123),存在服务器内存或 Redis 里,再把 ID 通过 Cookie 发给浏览器。之后每次请求,浏览器自动带上这个 Cookie,后端一查 ID,就知道你是张三还是李四。
优点很实在:简单、自带过期管理、天然防 CSRF(配合 SameSite 属性)、敏感信息不落客户端。
缺点也明显:服务端要存状态,横向扩展麻烦;多机部署得配共享存储(比如 Redis);移动端用起来稍拗口(得手动管 Cookie)。
token 是什么?像一张不记名电影票
你买好电影票,票面印着场次、座位、有效期,检票员扫一眼就放行——全程不用回售票处查记录。JWT 就是这种“自包含”的 token:用户登录成功后,后端签发一个字符串(比如 eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...xxx),里面直接塞了用户 ID、角色、过期时间,还带签名防篡改。前端存 localStorage 或内存里,每次请求放在 Authorization 头里发过去:
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
服务端收到后,验签名、解出字段,就知道该给谁开权限。不用查数据库,也不用存 session 记录。
适合前后端分离、APP、小程序、微服务间调用。但要注意:不能随便往 token 里塞太多数据(体积大、传输慢);一旦签发就无法主动作废(除非加黑名单或缩短有效期);本地存储有 XSS 泄露风险。
到底怎么选?三个关键问题一问就清楚
1. 你的项目是传统 Web 还是前后端分离?
如果是老派 MVC(比如 Django 模板渲染、PHP + HTML),session 更省心;要是 Vue/React 前端 + 独立 API 接口,token 几乎是标配。
2. 用户量和部署方式如何?
小站单台服务器,session 丢内存里完全够用;要是准备上云、做集群、跑 K8s,token 的无状态特性会少踩很多坑。
3. 安全需求偏哪边?
要精细控制登出(比如管理员踢人)、频繁修改权限,session 更灵活;若更看重跨域支持、移动端兼容、减少服务端负担,token 更合适。
一个小对比表,拿不准时瞄一眼
| 维度 | Session | Token(如 JWT) |
|---|---|---|
| 存储位置 | 服务端(内存/Redis) | 客户端(localStorage / 内存) |
| 是否需要查库验证 | 是(每次查 session ID) | 否(验签名+过期即可) |
| 登出控制 | 服务端删 session 即可 | 需额外维护黑名单或依赖短时效 |
| 跨域支持 | 需配置 CORS + withCredentials | 天然支持(Header 传就行) |
最后提醒一句:别迷信“新就是好”。见过用 JWT 存手机号、身份证号的,也见过硬在小程序里塞 session Cookie 结果反复 401 的。工具没有高下,用对地方才是真本事。