从遗留认证/授权迁移至自定义中央授权服务器的技术问询
方案合理性确认
当前采用的OIDC认证+客户端本地用户映射方案完全合理,非常适配你现有多单体应用的架构:
- 不需要改动单体应用核心的数据关联逻辑(原有业务表都绑定本地用户表),改造风险极低
- OIDC是工业级的SSO协议,ID Token的签名验证机制能有效保证身份合法性,避免伪造
- 保留客户端本地会话模式,和单体原有的表单登录逻辑兼容,用户体验无断层
但要注意几个关键细节:
- ID Token里必须携带客户端能精准匹配本地用户的标识,比如客户端的本地用户ID,或者
client_id+用户名的组合键(应对用户名重复场景) - 客户端必须严格校验ID Token的签名、过期时间、受众(
aud字段),绝对不能跳过验证直接信任 - 后续迁移授权逻辑时,可以在ID Token或Access Token中嵌入你自定义的角色/组信息,客户端无需再查询本地权限表,直接用Token中的权限信息做校验
问题1:存量用户同步解决方案
核心思路:全局唯一用户ID+客户端关联映射
解决用户名不唯一问题
SSO绝对不能用用户名作为用户主键,必须给每个用户生成全局唯一的UUID作为身份标识。新增一张user_client_mapping关联表,记录SSO用户ID、客户端ID、客户端本地用户ID三者的对应关系,以此区分不同客户端的同名用户,后续登录时结合client_id+用户名定位到唯一的SSO用户。
密码同步规范
- 绝对禁止同步明文密码,直接同步原应用的密码哈希值(比如BCrypt、SHA-256加盐哈希)
- 如果不同单体应用用了不同的密码哈希算法,SSO可以用Spring Security的
DelegatingPasswordEncoder实现多编码器适配,根据客户端ID匹配对应的加密算法
同步实施步骤
- 每个单体应用导出存量用户数据:包含本地用户ID、用户名、密码哈希、必要的用户属性(如邮箱、手机号)
- 编写批量导入脚本,把数据导入SSO的用户表和关联映射表,导入时自动生成SSO全局用户ID
- 增量同步:要么设置定时任务(比如每天凌晨)让客户端推送新增/修改的用户数据到SSO;要么在客户端用户变更时触发API调用实时同步
- 一致性校验:抽样验证同步后的用户能不能正常通过SSO登录,确保密码哈希匹配无误
问题2:新用户创建流程与同步机制
创建入口选择:优先统一在SSO创建
统一在SSO创建用户能保证身份全局唯一,避免多客户端重复创建用户。如果要兼容原有客户端的注册入口,也可以支持客户端发起创建请求。
统一SSO创建流程
- 用户在SSO的统一注册页面填写信息,完成身份校验(比如邮箱验证码)
- SSO创建全局用户,生成唯一用户ID,存储用户信息和密码哈希
- SSO根据预设的客户端配置(比如哪些客户端需要自动同步该用户),触发同步流程
- 客户端收到同步请求后,创建本地用户记录,关联SSO用户ID和本地用户ID
兼容客户端原有注册入口的流程
- 用户在客户端原有注册页面提交信息
- 客户端调用SSO的用户创建API,传递注册信息和自身的
client_id - SSO创建全局用户,返回SSO用户ID给客户端
- 客户端用返回的SSO用户ID创建本地用户记录
故障容错的同步机制
- 异步+重试:用消息队列(比如RabbitMQ)做异步同步,SSO创建用户后发送消息到队列,客户端消费消息创建本地用户。配置3次重试(间隔5分钟),失败消息进入死信队列,后续人工排查处理
- 幂等性保障:客户端创建用户时,以SSO用户ID作为唯一判断键,已经存在则跳过,避免重复数据
- 补偿机制:客户端添加定时任务(每小时/每天),拉取SSO近期新增的用户数据,对比本地表补全缺失的用户
- 同步日志:SSO和客户端分别记录同步日志,包含用户ID、客户端ID、时间、状态、失败原因,方便排查问题
内容的提问来源于stack exchange,提问作者Erfan Mirhoseini
相关产品推荐
相关产品推荐

