OIDC
OpenID Connect — 在 OAuth 2.0 之上做身份认证(Authentication)
OAuth 2.0 解决的是“授权(Authorization)”问题:第三方应用能在不知道你密码的情况下,代表你去访问你的数据。但它本身并不回答一个更基础的问题:“现在登录的是谁?” OIDC(OpenID Connect)就是为了解决这个问题而生的——它在 OAuth 2.0 的授权框架之上,增加了身份认证(Authentication)能力。
一句话概括:OAuth 2.0 管“你能做什么”,OIDC 管“你是谁”。
核心概念
OIDC 在 OAuth2 上的三处扩展
- ID Token:认证服务器除了发
Access Token之外,还会额外发一个ID Token。它是一个 JWT(JSON Web Token),里面直接携带了“用户是谁”的信息。 - UserInfo Endpoint:一个标准的资源接口(
/userinfo),拿着Access Token去调用,就能拿到结构化的用户资料(昵称、头像、邮箱等)。 - 标准化的 Scope:引入了
openid、profile、email等标准 scope,让“我要登录并拿到用户名”这件事有了统一写法。
4 个角色(与 OAuth2 一致,只是职责更明确)
- 用户(End User):你自己。
- 依赖方(Relying Party,RP):想登录你的第三方应用,对应 OAuth2 里的 Client。
- 认证服务器(OP,OpenID Provider):既负责认证你,又负责发 Token,例如微信、Google、GitHub。
- 资源服务器:持有你的用户资料的服务。
授权码模式 + OIDC 的流程
OIDC 最常用的是“授权码模式 + PKCE”,流程在 OAuth2 的 6 步之上多了“拿到 ID Token”这一步:
[ 用户 ] [ 依赖方 RP ] [ OP 认证服务器 ] [ UserInfo ]
| | | | |– 1. 登录 –>| | | |<– 2. 跳转登录页 —————-| | |– 3. 输密码同意 —————->| | |<– 4. 带回授权码 —————-| | | | | | | |– 5. 换 Token —>| | | |<– ID Token + Access Token ———-| | | | | |– 6. 带 Access Token 取资料 ——–>| | |<– 返回用户资料 ———————-|
关键区别:第 5 步换回来的响应里,除了 access_token,还会有一个 id_token。RP 校验签名后,直接从 id_token 里就能读出用户身份,不必再额外请求一次。
ID Token 里有什么(JWT Claims)
id_token 是一段 JWT,解码后是这样的字段(Claims):
iss:签发者,即 OP 的地址,用来确认 Token 是谁发的。sub:用户唯一标识(Subject),同一个用户在不同 RP 下sub通常稳定不变。aud:受众,必须等于 RP 的client_id,防止 Token 被别的网站冒用。exp/iat:过期时间 / 签发时间,用于判断 Token 是否还有效。nonce:RP 发起请求时带的随机串,原样返回,用来防重放攻击。name/picture/email:在 scope 申请了profile、email时才会出现的用户资料。
为什么需要 OIDC 而不是直接用 OAuth2
- OAuth2 没有“用户是谁”的标准答案:不同平台返回的用户信息格式五花八门(微信叫
openid,GitHub 叫login),接入每个平台都要写一套适配。 - OIDC 统一了身份语义:只要有
id_token+ 标准userinfo,任何 OP(微信、Google、Azure AD)对 RP 来说接入方式基本一致。 - 安全性更可控:JWT 自带签名与过期时间,RP 可以离线校验,不必每次都回 OP 查询。
与 OAuth2 的对比小结
| 维度 | OAuth 2.0 | OIDC |
|---|---|---|
| 解决什么 | 授权(你能访问什么) | 认证(你是谁) |
| 核心令牌 | Access Token | Access Token + ID Token |
| 用户身份 | 无标准定义 | 标准 JWT Claims + UserInfo |
| 典型场景 | 第三方代你调 API | 用微信/Google 一键登录 |