js实现单点登录
单点登录(SSO)实现原理
单点登录允许用户通过一次身份验证访问多个系统。核心机制是通过中央认证服务器(如Identity Provider, IdP)生成令牌(如JWT),其他系统(Service Provider, SP)验证令牌有效性。
基于JWT的SSO实现步骤
1. 用户登录认证

- 用户访问主系统(IdP)并提交凭证(如用户名/密码)。
- IdP验证凭证,生成JWT并返回给客户端(通常存储在Cookie或LocalStorage)。
// IdP服务器生成JWT示例(使用jsonwebtoken库)
const jwt = require('jsonwebtoken');
const token = jwt.sign({ userId: '123' }, 'secretKey', { expiresIn: '1h' });
2. 令牌传递与验证
- 用户访问子系统(SP)时,前端将JWT附加到请求头(如
Authorization: Bearer <token>)。 - SP后端通过公钥或共享密钥验证JWT有效性。
// SP服务器验证JWT示例
const decoded = jwt.verify(token, 'secretKey');
if (decoded.userId) {
// 认证通过
}
3. 跨域处理(可选)

- 若IdP与SP域名不同,需启用CORS或通过后端代理传递令牌。
- 使用
document.cookie设置SameSite=None和Secure属性以支持跨域Cookie。
OAuth 2.0集成方案
1. 授权码模式流程
- 用户访问SP,SP重定向到IdP授权页面。
- 用户授权后,IdP返回授权码至SP回调地址。
- SP用授权码向IdP换取访问令牌(Access Token)。
// SP后端换取令牌示例(使用axios)
const axios = require('axios');
const response = await axios.post('https://idp.com/token', {
code: 'AUTH_CODE',
client_id: 'SP_CLIENT_ID',
client_secret: 'SP_SECRET'
});
const accessToken = response.data.access_token;
2. 隐式模式(前端直接获取令牌)
- 适用于纯前端应用,IdP直接返回令牌至前端(通过URL哈希片段)。
// 前端解析哈希中的令牌
const token = window.location.hash.split('&')[0].split('=')[1];
安全注意事项
- JWT需设置短期有效期并启用HTTPS。
- 敏感操作需二次验证(如OTP)。
- 避免令牌存储在易泄露的位置(如全局变量)。
示例完整流程
- 用户登录
idp.example.com,获取JWT。 - 访问
sp1.example.com,前端携带JWT请求API。 - SP1验证JWT后返回数据。
- 用户访问
sp2.example.com时重复步骤2-3。
通过上述方法,可实现无感知的跨系统登录体验。






