Java后端用Azure Access Token验证用户时签名验证失败
解决OBO流调用Microsoft Graph时的AADSTS50013签名验证失败问题
问题核心
你遇到的AADSTS50013错误是因为前端传入的用户Token(断言)签名验证失败,结合错误信息里的占位符应用ID和固定密钥指纹,问题集中在Token有效性、Azure应用配置和代码参数三个维度。
排查与修复步骤
1. 检查前端Token的正确性
- 用JWT解码工具解析前端传入的
tokenToValidate:- 确认
aud(受众)字段值等于后端Java应用的clientId,而非https://graph.microsoft.com或其他值。OBO流要求断言必须是用户发给后端API的Token,不能是直接发给Graph的Token。 - 检查
exp(过期时间)是否未过期,iss(颁发者)是否匹配你的租户ID格式(如https://login.microsoftonline.com/你的租户ID/v2.0)。
- 确认
- 前端需调整登录请求的
scope,改为后端API的权限范围(例如api://<后端clientId>/.default),确保获取到针对后端API的Access Token。
2. 修正Azure AD应用配置
- 后端应用配置:
- 在Azure AD注册后端应用时,进入「公开API」页面,设置应用ID URI(如
api://<后端clientId>),并添加一个权限范围(如access_as_user)。 - 进入「API权限」页面,添加Microsoft Graph的委托权限(如
User.Read),并完成管理员同意。
- 在Azure AD注册后端应用时,进入「公开API」页面,设置应用ID URI(如
- 前端应用配置:
在前端应用的「API权限」中,添加后端API的权限(即上述步骤中创建的access_as_user范围),并完成权限同意。
3. 修复代码中的参数问题
你代码中的字符串使用了HTML转义的",这会导致clientId等参数实际为my_clientId这类占位符,而非真实的Azure应用信息:
- 将代码中的
"替换为普通双引号,填入真实的Azure应用注册值。 - 修正后的核心代码片段:
public void verifyAzureToken(String tokenToValidate) { final String clientId = "你的后端应用clientId"; final String tenantId = "你的租户ID"; final String clientSecret = "你的客户端密钥"; final List<String> scopes = Arrays.asList("https://graph.microsoft.com/.default"); final OnBehalfOfCredential credential = new OnBehalfOfCredentialBuilder() .clientId(clientId).tenantId(tenantId).clientSecret(clientSecret) .userAssertion(tokenToValidate).build(); if (null == scopes || null == credential) { System.out.println("Unexpected error"); return; } final TokenCredentialAuthProvider authProvider = new TokenCredentialAuthProvider( scopes, credential); final GraphServiceClient<Request> graphClient = GraphServiceClient.builder() .authenticationProvider(authProvider).buildClient(); try { com.microsoft.graph.models.User user = graphClient.me() .buildRequest() .get(); if (user != null) { System.out.println(user.givenName); } } catch (Exception e) { e.printStackTrace(); } }
4. 验证OBO流权限链
确保权限链完整:用户→前端应用→后端API→Microsoft Graph,每一层的权限都已正确配置并完成同意操作。
内容的提问来源于stack exchange,提问作者leH
相关产品推荐
相关产品推荐

