2. 用户身份认证(Authentication):Session-Cookie、JWT、OAuth2.0 在适配层的应用与对比
身份认证,说白了就是回答一个问题:「你是谁?」。在接口适配层,这个问题变得特别棘手——因为你不仅要验证用户身份,还得考虑不同后端系统、不同协议、不同安全等级之间的「翻译」问题。我这些年做接口适配,踩得最多的坑,其实都跟认证有关。
今天咱们就聊聊三种主流认证方式:Session-Cookie、JWT、OAuth2.0。它们在适配层怎么用?各自有什么脾气?我一个个说。
2.1 Session-Cookie:经典但「有状态」
Session-Cookie 是最传统的方案。用户登录后,服务端生成一个 Session ID,存在内存或 Redis 里,同时把 Session ID 通过 Set-Cookie 下发给浏览器。后续请求带上 Cookie,服务端查一下 Session 存储,就知道是谁了。
在适配层用 Session-Cookie,有个天然的问题——有状态。适配层本身是个网关或代理层,如果它要维护 Session 状态,就得引入共享存储(比如 Redis)。否则,请求打到不同的适配实例,Session 就丢了。
适配层用 Session-Cookie 的场景,我建议这样处理:
- 适配层不直接管理 Session,而是透传 Cookie 到后端业务服务
- 如果适配层需要做「登录态校验」,那就统一走 Redis 查询
- 注意 Cookie 的 Domain 和 Path 属性,别把 Cookie 泄露到不该去的地方
2.2 JWT:无状态,但小心「过期」
JWT(JSON Web Token)这几年特别火。用户登录后,服务端签发一个 Token,里面包含用户信息、过期时间等,客户端存着,每次请求带上。服务端验签就行,不需要查数据库。
适配层用 JWT 有个天然优势——无状态。每个请求都带着完整的身份信息,适配层验签通过后,直接转发。不需要 Redis,不需要 Session 同步。
但 JWT 也有坑。我遇到过最典型的问题:
- Token 太大:JWT 里塞了一堆用户信息,每次请求都带着,带宽浪费严重
- 无法主动失效:签发出去的 Token,在过期之前,服务端没法主动让它失效。用户改了密码,旧 Token 还能用
- 密钥管理:适配层验签需要拿到公钥或密钥,密钥轮换时容易出问题
适配层用 JWT 的最佳实践:
- Token 里只放必要信息(用户 ID、角色、过期时间),别塞大对象
- 过期时间别设太长,我一般设 15-30 分钟,配合 Refresh Token 使用
- 适配层做验签,不做签发。签发交给认证服务
- 密钥轮换时,适配层要支持多密钥并行验证
代码示例:适配层验签 JWT
// 适配层 JWT 验签示例(Node.js)
const jwt = require('jsonwebtoken');
function verifyToken(req, res, next) {
const authHeader = req.headers['authorization'];
if (!authHeader || !authHeader.startsWith('Bearer ')) {
return res.status(401).json({ error: 'Missing token' });
}
const token = authHeader.split(' ')[1];
try {
// 验签,同时支持多个公钥(密钥轮换)
const decoded = jwt.verify(token, getPublicKey(token), {
algorithms: ['RS256'],
issuer: 'auth-service'
});
req.user = decoded;
next();
} catch (err) {
return res.status(401).json({ error: 'Invalid token' });
}
}
2.3 OAuth2.0:授权协议,别当认证用
OAuth2.0 本质上是个授权协议,不是认证协议。很多人把它当认证用,其实不太对。OAuth2.0 解决的是「第三方应用如何获取用户资源的访问权限」这个问题。
在适配层,OAuth2.0 最常见的用法是:
- 适配层作为 OAuth2.0 的客户端,向认证服务器获取 Token
- 适配层验证 Token 的有效性(调用 introspection endpoint)
- 适配层把 Token 透传给后端服务
我做过一个项目,适配层要对接多个第三方系统的 API,每个系统都有自己的 OAuth2.0 认证流程。适配层得维护多个 Token 的获取、刷新、缓存逻辑。说实话,挺麻烦的。
2.4 三种方式对比
我整理了一张对比表,方便你快速参考:
| 维度 | Session-Cookie | JWT | OAuth2.0 |
|---|---|---|---|
| 状态 | 有状态(需共享存储) | 无状态 | 有状态(Token 需管理) |
| 适配层复杂度 | 低(透传即可) | 中(需验签) | 高(需管理 Token 生命周期) |
| 安全性 | 中(防 CSRF) | 高(防篡改) | 高(支持多种授权模式) |
| 扩展性 | 差(需共享存储) | 好(无状态) | 中(需 Token 管理) |
| 适用场景 | 单体应用、内部系统 | 微服务、前后端分离 | 第三方授权、开放 API |
2.5 适配层认证架构图
下面这张图展示了适配层如何处理三种认证方式:
2.6 适配层认证选型建议
说了这么多,到底选哪个?我个人的经验是:
- 内部系统、单体应用:Session-Cookie 够用,别折腾
- 微服务架构、前后端分离:JWT 更合适,无状态好扩展
- 对接第三方、开放 API:OAuth2.0 是标准,别自己造轮子
- 混合场景:适配层可以同时支持多种认证方式,根据请求来源做路由
嗯,认证这块就聊到这儿。记住一点:适配层的核心职责是「验证身份 + 透传身份」,而不是「管理身份」。把身份管理交给专门的认证服务,适配层保持轻量和无状态,这才是正道。