切换深色模式
Google Agent 身份方案与认证系统落地设计
核对日期:2026-10-04(Asia/Shanghai)。适用范围:公司 AI 客户端、用户自带的第三方本地 Agent、服务器沙箱。系统职责固定为认证和输出可信身份,业务授权交给项目。
本文包含两种内容:标为“Google 能力”的部分来自官方资料;标为“本系统设计”的接口、字段、TTL、数据模型和流程是建议实现,不能称为 Google 原生 API。文末给出可执行的本地反例实验和真实环境验收表。文档可作为实施规格;本次没有部署 Google 云资源,也没有完成真实账号登录联调。
1. 结论与实施路线
Google 没有一套能自动识别任意本地 Agent 软件来源的统一机制。需要按证据分别处理:
| 场景 | Google 能力 | 本系统需要实现 | 能对项目证明什么 |
|---|---|---|---|
| 公司或第三方桌面 Agent | Google 用户登录;原生 OAuth 支持授权码和 PKCE | 身份代理、实例登记、持钥证明、会话撤销 | 用户身份,以及已登记密钥的持有者;软件来源默认未验证 |
| 支持应用证明的客户端 | App Check,对接具体平台证明提供方 | 验证提供方结果、身份关联和证据有效期 | 提供方覆盖范围内的应用/设备事实 |
| Google 受支持运行环境里的 Agent | Agent Identity,基于 SPIFFE 的工作负载身份 | 信任域配置、外部 JWT 验证、内部身份映射 | 指定 Google 托管资源的工作负载身份 |
| 自建或其他云沙箱 | 可按平台使用 Workload Identity Federation | 对接可信工作负载签发方和实例映射 | 工作负载身份;不会自动成为 Google Agent Identity |
第一阶段先完成本地认证和统一身份输出;第二阶段接 Google 云端 Agent 的外部 OIDC 凭证;第三阶段为确实支持的平台增加应用证明。每个阶段都保留软件来源未验证的接入路径,由项目选择是否接受。
Google 官方能力来源:原生 OAuth、App Check、Agent Identity、工作负载身份。
2. 必须分开的身份与事实
| 概念 | 定义 | 不能作为替代证据 |
|---|---|---|
| 用户主体 | 外部身份源的 issuer + subject 映射出的内部用户 | 邮箱、模型输出的用户名、本地操作系统用户名 |
| 登记客户端 | 在认证系统登记的软件/开发者信息 | client_id 本身不是本地软件真实性证明 |
| Agent 登记 | 系统创建的逻辑 Agent 记录 | 用户填写的名称不能证明官方来源 |
| 本地实例 | 与公钥绑定的注册实例 | 持钥不证明二进制完整性或设备未被攻陷 |
| 云工作负载 | 已验证 iss + sub 指向的托管资源 | 不一定细到每个进程、容器副本或任务 |
| 用户关联 | 已登录用户与实例/任务的服务端绑定 | 创建者、所有者不等于当前用户委托 |
| 业务授权 | 项目自己的资源、动作、审批规则 | 认证成功不意味着可以访问资源 |
本系统认证用户、实例/工作负载及其有效关联;项目决定该身份能做什么。 登记准入、签发凭证的认证策略属于认证系统自己的管理边界,不接管项目的客户记录、退款额度或工具权限。
3. Google 能力与明确边界
3.1 本地 OAuth 与应用审核
Google 原生应用采用浏览器登录和授权码交换,支持 PKCE。桌面应用被视为无法保守共享秘密的客户端。S1
Google 品牌审核核实应用展示信息和域名等;敏感权限审核检查用途及合规材料。审核发生在登记和发布层面,不能当成每次请求的运行实例证明。S2
例子:第三方复制官方客户端的公开 client_id,使用自己的 PKCE 参数。即使完成登录,服务端也不能仅凭这个 ID 把它标成“官方客户端已验证”。PKCE 防护授权码交换,不能单独验证软件来源。
3.2 App Check
App Check 根据平台证明验证应用或设备,并发放短期凭证。Android 可使用 Play Integrity,Apple 可使用 App Attest/DeviceCheck,Web 使用 reCAPTCHA Enterprise;能力和保证取决于提供方。S4
普通 Windows/Linux 桌面 Agent 没有上述默认提供方提供的通用软件来源证明。自定义提供方需要自行建立可信证据;重新包装客户端自报哈希不能产生证明。应用证明与用户登录是独立事实,不能互相替代。
3.3 Google Cloud Agent Identity
Agent Identity 将 SPIFFE 身份关联到托管资源。Google Cloud 访问凭证有证书绑定机制;外部身份则通过信任域的 STS OIDC 签发方验证。S5
实施前分别确认能力状态:外部 OIDC 接入文档、Agent CLI 部署指南目前标为 Preview;区域表中部分基础服务为 GA。这不是同一个发布状态,不能用“某区域 GA”推导所有路径都已 GA。S6S8
外部受众的 OIDC ID Token 默认不绑定运行证书。 外部 API 仅验证 JWT 时仍按 bearer 凭证评估重放风险。不能把 Google Cloud 内部的绑定令牌保证直接套到外部 API。S6
4. 统一架构:两条入口,一个可信身份契约

图:使用 imagegen 生成。蓝色表示厂商能力,青色表示本系统集成设计;凭证交换与检查顺序以下文为准。
本系统建议采用服务端身份代理(Broker),让所有本地 Agent 登录你们的 OIDC 服务,Broker 再联合 Google 登录。这样第三方不必分别持有 Google 项目,Google 凭证也不必交给第三方 Agent。
这是一种本系统集成设计,不是 Google Agent Identity 的桌面版本。采用成熟 OIDC 服务实现浏览器会话、授权码、PKCE、令牌签发和 DPoP;若所选产品不支持 DPoP,不得宣称已完成实例绑定认证,需先补齐或改为明确标注的 bearer 会话。
5. 本地 Agent:端到端接入规格
5.1 Google 与 Broker 的配置
- 在 Google Auth Platform 创建测试/生产分离的项目与 Web application 客户端,设置受众、测试用户及品牌资料。
- 注册固定 HTTPS 回调,例如
https://identity.example.com/federation/google/callback。Google 客户端密钥仅保存在 Broker 服务端的密钥管理设施。 - 登录请求仅申请
openid;需要展示资料时才加profile email。认证模块不申请 Gmail/Drive 业务权限,不默认请求 Google 长期离线访问。 - Broker 使用 OIDC 库验证 Google ID Token,允许的用户 issuer 精确配置为 Google 文档支持的值,
aud为 Broker 的 Google Web 客户端 ID;nonce必须匹配当前登录事务;多受众时按 OIDC 校验azp。 - 内部用户由 Google
iss + sub映射;对官方支持的两个 Google issuer 写法,在完成验证后规范化为同一个内部签发方,避免生成两个用户。邮箱用于展示。Google Workspacehd只能在验证后的声明中使用,不能依据请求中的hd或邮箱后缀认定租户;租户关联来自管理员维护的身份映射。
Google Web 客户端步骤参考 S9,用户声明和验证参考 S12。如果公司不允许 Google 账号作为员工身份源,可将上游替换为企业 IdP,后续实例认证契约不变。
5.2 Agent 与 Broker 的登录
- 第三方客户端完成登记:用途、联系信息、回调规则。默认
software_origin=unverified。公司客户端登记也不直接变为来源已验证。 - 本地实例生成 P-256 密钥;私钥保存在操作系统密钥库,优先不可导出。不要将私钥放入提示词或项目目录。首次安装/重装默认生成新实例。
- 本地 OIDC SDK 打开随机 loopback 端口,使用
state、nonce、PKCE S256 向 Broker 发起授权码登录。采用支持 RFC 9449 的 SDK,用dpop_jkt将本次授权码事务绑定实例公钥指纹;token endpoint 校验 DPoP 持钥及同一指纹。实际产品不支持授权码密钥绑定时,必须记录剩余边界,不能仅靠请求体中的公钥进行绑定。 - Broker 联合 Google 登录。上游 Google 的
state/nonce与下游本地客户端事务分别保存,不能混用。浏览器会话使用 Secure/HttpOnly Cookie,并限制重定向地址。 - 本地客户端通过授权码 + PKCE 换取 面向实例登记 API 的短期访问令牌;令牌绑定当前 DPoP 公钥。服务端依据实际 DPoP 证明记录公钥指纹,忽略用户自行提交的可信身份字段。
- 调用实例登记接口。服务端显示登记名称、实例公钥指纹与“软件来源未验证”,由用户确认身份关联;这一步不是业务功能授权。
- 成功后得到
instance_id。后续请求通过已绑定密钥证明该实例,用户切换时重新认证并建立新用户会话,不能沿用旧用户上下文。
本地回调只能监听 127.0.0.1 或 ::1。除 loopback 端口例外外,重定向严格匹配;禁止把返回地址拼到任意域名。第三方 Agent 拿到的是你们的会话凭证,不是 Google ID Token。[原生应用标准 S11]
5.3 本系统接口契约
以下 /v1/* 为自定义业务接口;/authorize、/token、Discovery 等以所选 OIDC 产品为准。
| 接口 | 输入与认证 | 服务端行为 | 输出 |
|---|---|---|---|
POST /v1/instances | 登记 API 受众的 DPoP 访问令牌与 DPoP proof;登记客户端引用、用户确认事务 ID | 取已验证用户和 cnf.jkt;确认事务绑定同用户、客户端、公钥且未过期;原子消耗事务 | instance_id、证据状态;不发业务权限 |
POST /v1/identity-credentials | 实例会话的 DPoP 令牌与 proof;目标项目引用 | 检查实例/会话有效;从项目注册表确定 aud;用户和实例均取服务端记录 | 面向项目的短期、持钥绑定凭证 |
POST /v1/cloud-identities/authenticate | Google Agent OIDC bearer token,aud 必须为此认证入口 | 验证信任域、签名及声明;映射已验证工作负载;忽略自报用户 | 认证上下文;如另行签发内部凭证,TTL 不超过上游剩余寿命 |
POST /v1/user-bindings | 前端已认证会话;用户确认;平台认证身份 | 创建短期单次票据,绑定用户、指定工作负载、任务和目标受众 | 仅可信调度服务可取用的绑定票据 |
POST /v1/sessions/{id}/revoke | 会话所有者或认证系统管理员身份 | 撤销会话、阻止续签;写审计 | 撤销时间和状态版本 |
POST /v1/introspect | 已认证项目后端;待验证内部凭证 | 验证凭证和当前会话状态,返回身份事实 | active 与可信身份字段 |
项目引用是注册映射,不是项目业务权限。认证系统可以确认目标项目存在并签发对应受众凭证;是否允许访问项目资源由项目判定。未知目标不得让请求方任意定义 issuer/audience 或网络地址。
建议起始参数:登录事务/用户确认票据 120 秒、内部身份访问凭证 300 秒、DPoP proof 时间窗口 60 秒;这些是本系统默认设计值,不是 Google 产品保证。按实际 SDK 行为和风险约定调整。
5.4 DPoP 验证与续签
项目接收 Authorization: DPoP <access_token> 和独立 DPoP 头。验证凭证签名/受众/有效期后,继续校验 proof 的签名、公开 JWK、typ、htm、htu、iat、jti、ath 和公钥指纹是否等于凭证的 cnf.jkt。按 RFC 9449 处理 URL 规范化及服务端 nonce,拒绝重放。S13
跨实例 replay cache 用 Redis 等存储,键为公钥指纹 + proof jti,原子 SET NX EX;过期时间覆盖可接受的 proof 窗口和时钟偏差。先完成所有校验再消耗 proof。校验服务故障时不放行。
续签必须验证原会话、当前实例持钥和注销状态。刷新令牌必须绑定实例并进行轮换/重用检测,或第一阶段直接采用到期重新登录。不要把 Google refresh token 注入 Agent。DPoP 不能防止已经控制本地进程的攻击者使用其密钥发请求。
6. 云端 Agent Identity:配置、请求与校验
6.1 部署前置与路径选择
检查实际项目可用性、账单、组织/项目编号、地区、所需 API、操作者部署权限和已安装 SDK 的参数。不要把当前受支持 Google 运行环境推导为任意 Docker 沙箱均支持。
用于外部 OIDC 集成的两种官方部署入口是 Agent Runtime 的 identity_type=AGENT_IDENTITY,以及 Cloud Run 的 --identity-type=agent-identity。具体 API 启用、CLI 初始化及依赖按 S7 执行;区域核对 S8。部署身份与运行时调用业务资源的权限分开配置。
以下命令在 Google Cloud Shell / Bash 执行;变量均替换为自己的测试项目。命令会创建云资源并可能计费,本次没有执行。
bash
gcloud version
gcloud run deploy --help | grep -- '--identity-type'
gcloud config set project "$PROJECT_ID"
gcloud run deploy "$SERVICE_NAME" \
--image="$IMAGE_URL" \
--region="$REGION" \
--identity-type=agent-identity \
--no-allow-unauthenticated缺少该 flag、项目不具备访问资格或地区不支持时停止这条路径,记录错误并升级/核对资格;不自动退化成 service account 后仍称 Agent Identity。--no-allow-unauthenticated 控制入站访问,外部请求的出站身份另行取得。
不采用 Cloud Run 时,按 S7 创建 Agent CLI 工程,在生成工程的配置中启用 Agent Identity,完成本地功能验证后部署到受支持区域。CLI 模板内容和版本会变化,应保存锁文件、部署配置和版本输出。
6.2 云端请求示例
下面是与官方凭证获取接口一致的最小调用形态;依赖安装在隔离环境,并在实际 Google 运行环境验证后锁定版本。目标接口必须是你们实际部署的测试入口。
python
import os
from google.auth.transport.requests import AuthorizedSession
from google.oauth2 import id_token
audience = os.environ["IDENTITY_AUDIENCE"]
endpoint = os.environ["IDENTITY_ENDPOINT"]
credentials = id_token.fetch_id_token_credentials(audience=audience)
session = AuthorizedSession(credentials)
response = session.post(endpoint, json={}, timeout=10)
response.raise_for_status()
print(response.status_code) # 不输出令牌或完整身份响应本机 ADC 或普通服务账号拿到令牌不代表 Agent Identity 成功;必须在支持的运行环境检查签发方、SPIFFE 主体和部署配置。外部默认 bearer 凭证只证明持有有效令牌,不能证明每个 HTTP 请求都具有实例私钥。S6
6.3 部署配置清单
所有地址示例必须换成实际 HTTPS 测试服务;不要将示例 issuer/subject 当真实身份投入生产。
| 配置 | 来源与要求 |
|---|---|
GOOGLE_WEB_CLIENT_ID | Google Auth Platform 的 Web application 客户端 |
GOOGLE_WEB_CLIENT_SECRET_REF | 服务端密钥管理引用;不分发给本地客户端 |
GOOGLE_LOGIN_REDIRECT_URI | Google 登记的 Broker 固定回调,必须精确一致 |
BROKER_ISSUER / BROKER_JWKS_URI | 成熟 OIDC 服务实际部署的 issuer 和公开签名密钥地址 |
LOCAL_OIDC_CLIENT_ID | Broker 内登记的公开客户端;严格回调与 PKCE S256 |
AGENT_EXPECTED_ISSUER | 实际组织/项目的 STS 工作负载池 issuer;精确登记 |
AGENT_EXPECTED_SUBJECT | 从可信部署记录核对的 SPIFFE 主体,不能从首次请求直接授信 |
IDENTITY_AUDIENCE | 云端凭证的目标受众,与认证入口配置精确一致 |
IDENTITY_ENDPOINT | 认证入口实际 URL;可与 audience 不同,但须固定服务端配置 |
PROJECT_AUDIENCE | 项目注册表中的固定受众,项目验证器与签发方一致 |
REPLAY_STORE | 各验证副本共享的 Redis/等价原子存储 |
SIGNING_KEY_REF | Broker 签名密钥引用,公开 JWKS 不包含私钥 |
部署记录同时保存:CLI/SDK 版本、镜像 digest、实际区域、信任域、声明验证配置、凭证寿命及撤销窗口。受众字符串不依赖 URL 自动推断,也不从请求 Host 头决定。
6.4 外部验证端的固定配置
Google 用户登录 issuer 与 Google Agent issuer 分开配置。Agent issuer 示例:
text
组织级:
https://sts.googleapis.com/v1/organizations/ORG_ID/locations/global/workloadIdentityPools/TRUST_DOMAIN
项目级:
https://sts.googleapis.com/v1/projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/TRUST_DOMAIN
Discovery:EXPECTED_ISSUER + /.well-known/openid-configuration
JWKS:从可信 Discovery 的 jwks_uri 获取生产配置按登记租户维护精确 issuer 白名单。仅检查字符串以 sts.googleapis.com 开头不足以限制到自己的组织;禁止从未验证 JWT 任意 URL 获取 Discovery,避免 SSRF。
校验顺序:
- 限制令牌长度和结构。未验证 payload 只用于选择已登记配置,不当成身份事实。
- issuer 必须在白名单;从固定可信地址获取 Discovery,核对其中 issuer 与配置一致。限制 HTTPS、域名、超时、响应大小和重定向。
- 使用成熟 JWT/OIDC 库,通过可信 JWKS 和
kid验签;算法只取管理员允许集合与可信元数据的交集,拒绝none和不匹配密钥类型。拒绝令牌自带的jku/x5u网络地址。 - 验证精确
iss、目标aud、exp、iat、如存在的nbf及非空sub。多受众令牌按所选 OIDC 库规范处理,不自行猜测。 - 将验证后的
iss + sub映射成内部工作负载身份;注册映射属于认证记录。未登记主体不自动标成公司 Agent。 - 输出认证结果。项目另查可信工作负载是否被允许执行该业务操作。
JWKS 缓存遵守服务器 Cache-Control;未知 kid 限速刷新一次,仍不存在则拒绝。缓存过期且刷新失败时不接收新凭证;有效缓存中的已知公钥仍可用于未过期凭证。不要每请求下载一次,也不要无限使用过期缓存。
官方外部集成给出了信任域 issuer、公开 Discovery/JWKS、标准声明验证及公钥轮换方式。S6 本系统的长度限制、租户映射、错误码和缓存失败策略是实现要求。
6.5 云端 Agent 与用户身份的关联
云端 SPIFFE token 默认表达工作负载主体,不能据此生成用户身份。推荐由前端认证会话创建短期、单次的用户绑定票据:
text
前端用户会话 → 认证系统创建绑定票据
↓ 绑定 user + workload + task + audience + expiry
可信平台调度到指定工作负载
↓
沙箱提交:有效工作负载凭证 + 绑定票据
↓
认证系统验证双方,原子消耗票据,建立短期任务会话票据不可仅按 task_id 查询获取;需随机不可猜标识、加密传输、受信任调度方认证及精确工作负载匹配。任务、实例和身份映射来自服务端记录,不能相信沙箱填写的 user_id。
如果 Google 工作负载身份只到 Cloud Run service 或 Agent 托管资源粒度,不能把它当容器副本身份。需要单沙箱隔离时,另由可信平台签发实例凭证并与调度记录绑定。原生资源粒度没有改变时,按资源身份报告。
自主后台任务没有当前用户,则不签发 user_id;创建者和 owner 仅作管理信息。证明用户关联不代表证明用户授权了所有动作,后者由项目维护。
7. 给项目的统一凭证与认证 SDK
以下为本系统 JWT 示意,不是 Google token 格式;示例 ID 和时间均为虚构。内部令牌采用不同于上游的签发密钥及 issuer,typ=at+jwt,项目按本系统固定契约验证。
json
{
"iss": "https://identity.example.com",
"aud": "https://project.example.com/api",
"sub": "instance:inst-789",
"iat": 1791100800,
"exp": 1791101100,
"jti": "credential-unique-id",
"tenant_id": "tenant-001",
"agent_registration_id": "agent-123",
"registered_client_id": "client-456",
"user_id": "user-001",
"session_id": "session-001",
"runtime_type": "local",
"software_origin": "unverified",
"authentication_methods": ["federated_user_login", "instance_key"],
"cnf": { "jkt": "public-key-thumbprint" }
}云端凭证 sub 使用内部工作负载主体;必要时记录 upstream_issuer/upstream_subject 或服务端证据引用。Google 云端签发方验证通过只说明托管资源身份,不填写 software_origin=official_verified。本地 agent_registration_id 是登记信息,不是不可伪造的软件品牌。
外部 Google ID Token 默认 bearer,内部转换成 DPoP 时必须另验证并绑定新的持钥证明,不能只复制 cnf。转换只能加强后续凭证的持钥要求,不能倒推上游 bearer 交换已具备防重放。高风险部署需另外建立可信通道/工作负载证明,或由项目不接受该认证方式。
认证入口返回给 Agent 的普通 JSON 仅用于展示,不能转发给项目充当证明。项目必须验证本系统签名凭证,或通过后端认证通道调用验证接口。单项目也可直接验证 Google Agent 凭证,但不可把发给 Broker 的受众令牌直接发给项目使用。
项目认证 SDK 返回不可由请求体覆盖的结构:
text
AuthenticatedPrincipal {
subject, tenantId, userId?, agentRegistrationId?,
sessionId, runtimeType, authenticationMethods,
softwareOrigin, evidenceReference?, credentialExpiresAt
}业务处理顺序:认证中间件 → 可信 Principal → 项目授权中间件 → 业务操作。直连后端时删除/覆盖外部 X-User-Id 等头;如网关传身份,后端仅信任经过认证的网关连接,阻断绕过网关路径。项目不能直接信任 Agent 自报身份。
**ID Token 边界:**用户登录 ID Token 发给登录客户端,不能任意当业务 API 凭证。Google Agent 外部 OIDC ID Token 则是官方设计的工作负载认证凭证,必须校验该外部服务的 audience。这两种使用场景不能混淆。
8. 数据模型、错误与生命周期
| 表 | 必要字段与约束 |
|---|---|
external_subjects | issuer、subject、internal_user_id;issuer+subject 唯一;租户成员关系独立维护 |
client_registrations | client_id、公开名称、开发者、审核状态、回调规则;品牌审核与软件来源分列 |
instances | instance_id、registration_id、jkt、status、created_at、last_seen;密钥更换须重认证并撤销旧关联 |
workload_mappings | exact_issuer、exact_subject、tenant_id、agent_registration_id、status;精确关联,禁止字符串模糊匹配 |
login_transactions | state_hash、nonce、PKCE挑战、client、redirect、jkt、expiry、consumed;一次性事务 |
sessions | session_id、user_id 可空、实例/工作负载、tenant、version、status、expiry |
binding_tickets | ticket_hash、user、workload、task、audience、expiry、consumed;原子消耗 |
authentication_evidence | issuer、证明类型、结果、有效期、主体引用、证据摘要;不存原始访问令牌 |
一次性对象使用事务或 Redis 原子操作消耗;并发两次兑换最多一次成功。认证关联更换不能靠客户端覆盖数据库字段。
| 对外结果 | 含义 | 内部诊断示例 |
|---|---|---|
401 | 凭证或认证关联无效 | invalid_signature、wrong_audience、expired、proof_replayed、session_revoked |
400 | 请求格式或参数无效 | malformed_request、unknown_target |
409 | 实例登记冲突或事务已消耗 | binding_conflict、transaction_consumed |
429 | 认证或公钥刷新限速 | login_rate_limited、jwks_refresh_limited |
503 | 无法可靠完成认证 | replay_store_unavailable、jwks_unavailable |
项目 403 | 已认证但项目授权拒绝 | 此判断由项目返回,认证系统不代判 |
对外不披露完整密钥、票据、token 或过多租户信息。审计记录 correlation_id、主体、实例/工作负载、认证方法、结果、失败分类、时间;不写 Authorization、DPoP 原文、授权码或刷新令牌。
注销/撤销必须定义生效边界:纯离线验签的项目可能继续接受令牌到期(建议最长 300 秒);要求更快失效时项目认证 SDK 调用 introspection,或订阅撤销状态并约定缓存窗口。撤销用户关联不等于已经撤销外部 SaaS 令牌,也不回滚已提交业务操作。
签发密钥在 KMS/HSM 中管理,轮换保留旧公钥覆盖已签发凭证寿命;登录回调、绑定确认和续签分别限速。浏览器账号切换、Agent 重装、密钥丢失和沙箱销毁均须有明确的重新认证/撤销路径。
9. Google 用户委托、OBO 与授权范围
若仅输出身份,不需要引入第三方业务 Token Vault。Google Agent Identity auth manager 的三方 OAuth(3LO)用于用户同意访问外部服务并管理服务凭证;它不是任意身份 token 转成任意 SaaS token 的通用 OBO。S14
项目若要接 Google Drive、Jira 等,项目自行申请所需授权、维护同意和资源权限。认证系统可以输出用户主体映射,不能因已登录 Google 就声明已获准读邮件或文件。认证-only 架构中不签发 refund:write 等业务权限、不维护项目资源 ACL。
10. 实施交付顺序与上线门槛
| 阶段 | 实施内容 | 可审查产物 |
|---|---|---|
| A:基础联邦登录 | 配置 Google Web client、Broker OIDC、用户映射、两个登录事务 | 脱敏配置、真实登录成功/错误 state/错误 nonce 记录 |
| B:本地实例 | DPoP、实例登记确认、短期凭证、注销与重装 | 两个用户与两个实例的隔离结果、密钥替换与重放反例 |
| C:项目接入 | SDK 验签、固定受众、Principal、在线状态、项目自主授权 | 401/403 的独立证据、绕过网关反例 |
| D:Google 云端 | 确认资格/版本/区域、启用 Agent Identity、STS OIDC 校验 | 部署状态、脱敏 iss/aud/sub、真实 JWKS 轮换验证 |
| E:用户与沙箱 | 可信调度、单次绑定票据、任务会话 | 错工作负载、换用户、并发兑换和任务取消反例 |
| F:来源加强 | 支持的平台接 App Check/受管终端证明 | 验证证据范围、过期行为;桌面无证据仍标未验证 |
每阶段记录:配置版本、SDK/CLI 精确版本、测试输入、期望、实际结果、correlation_id 与脱敏证据。上线前所有所选路径的实测门槛必须通过;文档核对和离线实验不能代替 Google 真实联调。
11. 验收矩阵与本次验证
11.1 可重复的本地反例实验
powershell
node --test docs/public/examples/google-agent-identity-lab.test.mjs
pnpm docs:build若 Windows 执行环境禁止测试器派生进程,可在 Node.js 24 下运行等价的单进程命令:node --test --test-isolation=none docs/public/examples/google-agent-identity-lab.test.mjs。本次使用此方式通过 50 项检查。
实验使用运行时生成的 RSA/EC 密钥及合成 JWT,执行真实签名验证;上游网络用固定可信 JWKS 模拟。覆盖 JWT 篡改、签发方/受众、算法、时间、轮换、DPoP 持钥与重放、用户绑定票据及注销窗口。实验代码不是生产认证 SDK,未实现完整 OAuth 服务、真实 Google 登录、App Check 或 Google 云部署。
11.2 必须在真实环境补齐的验收
| 编号 | 实测动作 | 通过标准 | 本次状态 |
|---|---|---|---|
| G01 | 两个 Google 测试用户分别登录 | 主体不同,邮箱不充当主键;错误 state/nonce 被拒绝 | 未实测 |
| G02 | 官方名称/client_id 被第三方复制 | 软件来源仍未验证,不升级身份保证 | 未实测 |
| G03 | 截获授权码后用另一 PKCE verifier 兑换 | 兑换失败;回调仅 loopback | 未实测 |
| G04 | 两个本地实例互换访问令牌 | DPoP 公钥不匹配,项目返回 401 | 未实测 |
| G05 | 同一个 proof 并发请求两个项目副本 | 全局 replay cache 最多一次接受 | 未实测 |
| G06 | 注销/换用户/密钥丢失 | 续签拒绝;在线校验立即拒绝,离线不超过约定窗口 | 未实测 |
| G07 | Google 测试云部署并请求外部 OIDC token | 确認为 Agent Identity 的 STS issuer 与 SPIFFE sub,而非普通服务账号 | 未实测 |
| G08 | 外部 OIDC token 发给错误受众/信任域 | 验证端拒绝;不访问不可信 Discovery 地址 | 未实测 |
| G09 | 真实密钥轮换、JWKS 故障 | 未知 kid 有界刷新;过期缓存且刷新失败则拒绝 | 未实测 |
| G10 | 将 bearer token 复制到另一环境 | 记录外部默认凭证可重放边界;不得宣称证书绑定 | 未实测 |
| G11 | 云工作负载提交别人的 user_id/绑定票据 | 自报用户忽略,错工作负载/过期/重复票据拒绝 | 未实测 |
| G12 | 已认证用户尝试无权限的项目资源 | 认证成功,项目独立返回 403 | 未实测 |
| G13 | 真实 App Check 证明过期/无效 | 提供方验证拒绝;来源状态不自动保留为有效 | 未实测 |
| G14 | 浏览器和目标区域网络可达性 | 登录、STS、JWKS 可达;记录超时/限速行为 | 未实测 |
G01–G06、G12 是本地路径的上线门槛;G07–G11 是云端路径的上线门槛;G13 仅在启用来源证明时适用;G14 两条路径均适用。没有真实 Google 账号/项目和部署环境,本次不会把这些行改为“通过”。
本次核验结论与运行证据见 验证报告。知识库页面的报告摘要:官方能力边界已核对;本地实验与站点构建结果以报告为准;Google 真实登录/部署/App Check 留为上线前门槛。
12. 完整案例:本地发起、云端执行、项目判权
本节是本系统设计案例,把前文的接口、数据模型与生命周期串起来,不增加 Google 原生能力的承诺。用户小林用第三方本地 Agent 发起一次“汇总项目工单”任务,实际计算运行在 Google 托管 Agent,项目仍自行控制工单访问权限。
12.1 建立本地会话
- 第三方 Agent 生成实例密钥并经浏览器向 Broker 登录。Broker 联合 Google 验证用户,得到稳定外部主体,映射为内部用户。
- Broker 和本地端完成此前定义的 PKCE、事务及持钥校验。实例登记将该用户、客户端记录与实际验证过的公钥关联。
- Broker 输出会话,但软件来源仍为
unverified。登记名称即使写成“公司官方 Agent”,也不影响这个事实。 - 小林选择项目并创建任务。服务端从当前认证上下文读取用户,不从任务说明或 JSON 中的
user_id读取身份。
此时已知的是用户身份和实例持钥事实;尚不能推导“后续任意云任务都代表小林”。云任务关联需要下一步单独建立。
12.2 将用户绑定到指定云任务
可信调度端创建一次性绑定票据,绑定小林、目标工作负载、任务 ID 和认证入口受众。票据通过受保护调度通道传递,不能放在 Agent 会交给模型阅读的任务正文中。
Google 托管 Agent 取得面向本系统认证入口的 OIDC 凭证。Broker 先验证其 issuer、签名、SPIFFE subject、受众和时间,再核对部署登记;通过后才能消费该工作负载对应的票据。
消费时原子检查票据的任务、主体、受众、时效和已用状态。一张合法票据若交给另一工作负载,仍必须失败。两个副本同时兑换时只有一个成功;重试需要通过既定幂等事务查询结果,不能重复建立新关联。
12.3 访问项目时保留哪些身份
| 字段 | 本例含义 | 证据来源 |
|---|---|---|
| 用户 | 小林的内部用户 ID | 已验证登录及有效用户绑定 |
| 当前 actor | 云端 Agent 的工作负载映射 | 已验证 Google 工作负载凭证 |
| 发起实例 | 第三方本地实例记录 | 原始受认证会话,作为关联信息 |
| 软件来源 | 第三方本地端未验证 | 没有应用证明,不作升级 |
| 目标受众 | 工单项目固定 audience | 项目注册配置 |
“发起实例”不能被误写成云请求的当前持钥者。外部 Google OIDC 凭证默认 bearer 的性质,也不会因为任务起点使用 DPoP 就自动改变。
Broker 为该会话签发工单项目凭证,寿命受上游证据、绑定和自身会话约束。项目验证后,用小林及当前 actor 检查工单范围。结果可以是认证成功、项目拒绝;两者不矛盾。
12.4 四个实际故障如何处理
| 情况 | 处理方式 | 不应采取的动作 |
|---|---|---|
| 小林切换为另一个账号 | 新建用户会话和任务关联 | 只替换展示名,沿用旧绑定 |
| 本地 Agent 重装丢失密钥 | 登记新实例,旧实例按规则撤销 | 仅凭旧 instance ID 恢复持钥身份 |
| 云工作负载部署身份变化 | 核对登记,重新建立可信映射 | 首次见到新 subject 就自动信任 |
| 小林撤销任务会话 | 停止续签,项目按撤销契约拒绝 | 继续使用缓存身份创建新凭证 |
若项目仅离线验签,已签发的短期凭证可能在剩余有效期内继续可用;要求更快失效的项目采用在线验证或受控撤销机制,并实际测量传播时间。
12.5 如何从日志解释这次调用
日志链应能从本地登录事务关联到实例登记、任务绑定、工作负载验证、项目凭证签发和项目决策。使用不可猜测的关联 ID,保存主体与配置版本;不保存可重放的原始凭证。
对外可以准确解释为:“经用户登录确认的任务,由指定云工作负载执行;工单项目根据用户和调用者身份决定访问范围。”不能解释为“认证平台保证了模型执行的每个动作都符合用户意图”。身份认证与任务语义控制是不同的工程问题。
13. 官方资料与标准
- S1:Google 原生 OAuth:桌面客户端、PKCE、回调和共享秘密边界。
- S2:品牌审核:登记品牌和域名审核。
- S3:敏感权限审核:业务 scope 审核。
- S4:Firebase App Check:平台证明、提供方和保证范围。
- S5:Agent Identity 概览:受支持运行环境与工作负载身份。
- S6:Agent 外部 OIDC 认证:Preview、外部默认非绑定凭证、STS issuer/JWKS、校验。
- S7:创建部署 Agent Identity:Preview、CLI、前置配置。
- S8:Agent Identity 地区:逐地区发布状态。
- S9:Google Web OAuth:服务端客户端与回调。
- S10:Google 工作负载身份:其他云和运行环境的接入区别。
- S11:RFC 8252:原生应用认证与 PKCE。
- S12:Google 用户 ID Token 验证、OIDC Core:用户身份及声明验证;授权码登录遵循 OIDC 库的 state/nonce 事务校验,不照搬 GIS POST 回调示例。
- S13:RFC 9449:DPoP 持钥证明;本文设计不声称 Google 桌面 OAuth 原生签发 DPoP 令牌。
- S14:Google auth manager 3LO:用户同意与外部服务凭证。