oauth2 oidc saml 对比
前言
在单点登录(SSO)和身份认证领域,OAuth2、OIDC(OpenID Connect)和 SAML 是目前使用最广泛的三种协议。它们经常被同时提到,但解决的问题却并不完全相同:
- OAuth2:解决授权(Authorization)问题——“允许第三方应用访问我的资源”。
- OIDC:在 OAuth2 基础上扩展,解决认证(Authentication)问题——“证明我是谁”。
- SAML:一个较早期的、基于 XML 的认证+授权协议,主要用于企业 SSO。
本文作为自己的笔记,用于系统梳理三者的关系、差异及各自的适用场景。
一、核心概念对比
1.1 一句话定义
| 协议 | 全称 | 核心定位 | 诞生时间 |
|---|---|---|---|
| OAuth2 | Open Authorization 2.0 | 授权框架:让第三方应用在用户授权下访问受保护资源 | 2012(RFC 6749) |
| OIDC | OpenID Connect 1.0 | 身份认证层:基于 OAuth2 之上的身份认证协议 | 2014 |
| SAML | Security Assertion Markup Language | 认证+授权协议:基于 XML 的企业级 SSO 协议 | 2005(SAML 2.0) |
1.2 关键差异速览
| 维度 | OAuth2 | OIDC | SAML |
|---|---|---|---|
| 主要用途 | 授权(Authorization) | 认证(Authentication) | 认证 + 授权 |
| 数据格式 | JSON | JSON / JWT | XML |
| 传输方式 | HTTP + Bearer Token | HTTP + Bearer Token | HTTP POST / Redirect(XML 签名) |
| 令牌类型 | Access Token(+ Refresh Token) | ID Token(JWT)+ Access Token | SAML Assertion(XML) |
| 用户身份信息 | 不包含(需额外接口获取) | 包含在 ID Token 中 | 包含在 SAML Assertion 中 |
| 适用场景 | 开放平台、API 授权 | Web / 移动端 SSO、社交登录 | 企业内部 SSO、B2B |
| 复杂度 | 中 | 中 | 高 |
| 移动端支持 | 好 | 好 | 差 |
二、OAuth2 详解
2.1 角色定义
- Resource Owner(资源所有者):通常是用户本人。
- Client(客户端):希望访问用户资源的第三方应用。
- Authorization Server(授权服务器):签发 Access Token。
- Resource Server(资源服务器):存放用户资源,校验 Token 后返回数据。
2.2 四种标准授权模式
- 授权码模式(Authorization Code):最常用、最安全,适用于有后端的 Web 应用。
- 简化模式(Implicit):纯前端应用,已不推荐,改用 PKCE。
- 密码模式(Password):客户端直接持有用户密码,信任度要求极高。
- 客户端模式(Client Credentials):无用户参与,应用对应用授权。
新增扩展:PKCE(公共客户端保护)、Device Code(设备码模式,适用于电视/IoT)。
2.3 授权码流程(简图)
1 | sequenceDiagram |
2.4 OAuth2 的局限
- 只管授权不管认证:Access Token 仅表示”有权限访问某资源”,并不能直接证明”用户是谁”。
- 无标准化的用户信息接口:不同厂商的
userinfo接口字段不统一(这也是 OIDC 出现的原因)。 - Token 格式不统一:既可以是随机字符串(opaque),也可以是 JWT。
三、OIDC 详解
3.1 与 OAuth2 的关系
一句话概括:OIDC = OAuth2 + 身份认证层(ID Token) + 标准化 UserInfo 接口。
OIDC 完全复用 OAuth2 的授权流程和端点,只是在此基础上:
- 新增
openid这个 scope,用于标识这是一个身份认证请求。 - 在 Token 响应中额外返回一个 ID Token(JWT 格式)。
- 标准化了
/userinfo端点与用户属性字段(如sub、email、name)。 - 标准化了 Discovery(
/.well-known/openid-configuration)与 JWK 公钥端点。
3.2 ID Token 结构
ID Token 是一个标准的 JWT,包含如下典型 Claims:
1 | { |
客户端收到后通过 IdP 的公钥验签,即可安全识别用户身份,无需再调用接口。
3.3 OIDC 与 OAuth2 的核心差异
| 维度 | OAuth2 | OIDC |
|---|---|---|
| 解决的问题 | 授权 | 认证(+ 授权) |
| 额外的 scope | 自定义 | 必须包含 openid |
| 返回的令牌 | Access Token | Access Token + ID Token |
| ID Token 格式 | —— | 必须是 JWT |
| 用户信息获取 | 厂商自定义接口 | 标准 /userinfo 端点 |
| 元数据发现 | 无标准 | 标准 Discovery 文档 |
| 是否能表明”我是谁” | 不能(Access Token 不应被客户端解析) | 能(ID Token 是为客户端设计的) |
⚠️ 常见误用:很多系统直接把 OAuth2 的 Access Token 当作”登录凭证”使用并解析其内容,这是反模式。Access Token 是给资源服务器用的,ID Token 才是给客户端用来识别用户身份的。
3.4 典型流程
OIDC 的 Authorization Code Flow 与 OAuth2 几乎一致,只是请求中带上 scope=openid:
1 | GET /authorize? |
拿到 code 后换 token 时,响应会同时返回 access_token 与 id_token。
四、SAML 详解
4.1 角色定义
- Principal:终端用户。
- Service Provider(SP):服务提供方(业务系统)。
- Identity Provider(IdP):身份提供方(统一认证中心)。
4.2 核心流程(SP-Initiated SSO)
1 | sequenceDiagram |
4.3 SAML Assertion
SAML 的”令牌”是一段 XML,包含三类声明:
- Authentication Statement:认证方式、时间。
- Attribute Statement:用户属性(邮箱、部门、角色等)。
- Authorization Decision Statement:授权结论(可选)。
使用 XML 签名(XMLDSig)保证完整性,可选 XML 加密保护敏感字段。
4.4 特点
- 基于 XML:报文大、解析复杂、对浏览器原生不友好。
- 依赖浏览器:主要靠 HTTP-Redirect / HTTP-POST binding,移动端和 SPA 不方便。
- 企业友好:与 AD FS、Okta、Azure AD、Keycloak 等企业身份源无缝集成。
- 一次登录,多系统互通:是传统企业 SSO 的事实标准。
五、三者关系总览
1 | graph TB |
- OIDC 是 OAuth2 的超集:所有 OIDC 服务都是 OAuth2 服务,反之不成立。
- SAML 与 OIDC 在功能上有重叠,都能做 SSO,但技术栈和生态完全不同。
- 现代新系统优先选择 OIDC;遗留企业系统常见 SAML;开放平台 API 使用 OAuth2。
六、使用场景对比
6.1 OAuth2 典型场景
- 开放平台 API 授权:如 GitHub、微信开放平台,允许第三方应用代表用户调用 API。
- 前后端分离应用的资源访问控制:自家应用的 API 鉴权(虽然严格来说这是简化用法)。
- 服务间调用(Client Credentials):微服务之间的 M2M 认证。
- IoT / 设备授权(Device Code):电视、打印机等无键盘设备。
6.2 OIDC 典型场景
- 社交登录 / 第三方登录:Google、Apple、微信(微信更接近 OAuth2)等”Sign in with XXX”。
- 企业内部新建系统 SSO:使用 Keycloak、Auth0、Azure AD 作为 IdP。
- 移动端 App 登录:配合 PKCE 的 Authorization Code Flow。
- Zero Trust 架构下的身份层:统一身份源,下发 JWT。
6.3 SAML 典型场景
- 大型企业内部 SSO:如 Office 365、Salesforce、Jira、Confluence 等企业 SaaS 接入公司 AD。
- B2B 联邦身份:公司 A 的员工通过公司 A 的 IdP 登录公司 B 的系统。
- 政务、金融等对合规要求高的场景:SAML 成熟、审计链路清晰。
- 遗留系统整合:许多老牌 SaaS 仍以 SAML 为首选接入方式。
七、如何选型
| 你的需求 | 推荐协议 |
|---|---|
| 我要做”微信登录/Google 登录”这样的第三方登录 | OIDC(或封装过的 OAuth2) |
| 我要开放 API 让别的公司/开发者接入 | OAuth2 |
| 公司内部要做几十个系统的统一登录,且多为 Web 应用 | OIDC(新建)或 SAML(历史原因) |
| 公司要接入 Salesforce / Workday / Office 365 等企业 SaaS | SAML(通常只能选它) |
| 移动端 / SPA 登录 | OIDC + PKCE |
| 微服务之间的机机调用 | OAuth2 Client Credentials(或 mTLS) |
| 设备类登录(无键盘) | OAuth2 Device Flow |
八、常见疑问(FAQ)
Q1:OIDC 既然能做认证,是否还需要 OAuth2?
A:OIDC 本身就是 OAuth2 的扩展,部署 OIDC 时天然就包含 OAuth2。真正的问题是”要不要用 ID Token 代替 Access Token 做鉴权”——不要,两者职责不同。
Q2:能用 SAML 代替 OIDC 吗?
A:功能上大部分可以,但 SAML 在移动端、SPA 上体验差,且 XML 对开发者不友好,新系统不推荐。
Q3:Access Token 为什么不能用来识别用户?
A:Access Token 是”访问凭证”,其格式、受众都是资源服务器,客户端不应对其做解析。用 ID Token 或调用 /userinfo 才是正确做法。
Q4:JWT == OIDC 吗?
A:不等于。JWT 只是一种令牌格式,OIDC 强制 ID Token 为 JWT,但 OAuth2 的 Access Token 可以是 JWT 也可以是 opaque string。
Q5:SAML 已经过时了吗?
A:在企业 SaaS 市场仍然是主流,短期内不会消失;但新系统设计优先考虑 OIDC。
九、总结
- OAuth2 是授权,OIDC 是认证,SAML 是早期的企业级认证+授权。
- OIDC 建立在 OAuth2 之上,通过 ID Token 和标准化的 UserInfo 接口补齐了”身份认证”能力。
- SAML 和 OIDC 目标类似,但技术栈分别是 XML 和 JSON/JWT,生态上 SAML 偏企业传统系统,OIDC 偏现代 Web/移动应用。
- 选型时以业务场景 + 接入对象为准:开放 API 选 OAuth2,用户登录选 OIDC,企业 SaaS 互联选 SAML。
