Angular 5中通过ADAL获取Id_token后如何获取Access Token及解决Graph API报错
解决Angular 5中ADAL调用Microsoft Graph API的"Access token validation failure"错误
我来帮你搞定这个问题——你目前遇到的核心问题是误把id_token当成了access token来调用Graph API,而且没有正确获取针对Graph资源的授权token。下面一步步给你拆解原因和解决方案:
先搞懂两个token的区别
id_token:这是身份令牌,只用来验证用户身份(证明"你是谁"),它的受众(aud字段)是你的应用clientId,不能用来访问像Graph API这样的外部资源。access_token:这是授权令牌,专门用来访问特定的API资源,每个资源(比如Graph、Azure Storage等)对应的access token是独立的,它的受众必须是目标API的地址(比如Graph的就是https://graph.microsoft.com)。
具体解决方案
1. 确保ADAL配置或请求时指定Graph API资源
ADAL默认会请求你应用自身的资源token,所以你需要明确指定Graph API作为目标资源:
// 初始化ADAL时指定Graph资源(推荐) this.adalService.init({ clientId: this.secretService.adalConfig.clientId, resource: 'https://graph.microsoft.com', // 关键:告诉ADAL我们要访问Graph API // 其他配置(比如redirectUri、tenant等)... });
2. 正确获取Graph API的Access Token
不要直接用clientId去拿缓存token,而是要针对Graph资源来获取:
const graphResource = 'https://graph.microsoft.com'; // 先尝试从缓存获取 let accessToken = this.adalService.getCachedToken(graphResource); if (!accessToken) { // 缓存没有的话,主动发起请求获取 this.adalService.acquireToken(graphResource) .subscribe( token => { accessToken = token; this.callMeGraphEndpoint(accessToken); }, err => console.error('获取Graph token失败:', err) ); } else { // 直接用缓存token调用API this.callMeGraphEndpoint(accessToken); }
3. 调用Graph API时正确携带Token
确保请求头里的Authorization格式正确:
private callMeGraphEndpoint(token: string) { this.http.get('https://graph.microsoft.com/v1.0/me', { headers: new HttpHeaders({ 'Authorization': `Bearer ${token}` }) }).subscribe( res => console.log('Graph API返回数据:', res), err => console.error('调用Graph失败:', err) ); }
4. 检查Azure AD应用的权限配置
别漏了这一步!你需要在Azure AD应用注册里:
- 添加Microsoft Graph的委托权限(比如
User.Read,这是调用/me接口需要的); - 如果是企业应用,需要管理员同意该权限(否则普通用户可能无法获取到有权限的token)。
常见坑点提醒
- 检查token的
aud字段:可以用jwt.ms解码token,Graph API的access token的aud必须是https://graph.microsoft.com,如果是你的clientId,那说明拿的是id_token或者错误资源的token; - 如果之前已经登录过,缓存里可能只有旧资源的token,这时候必须显式调用
acquireToken指定Graph资源来刷新。
内容的提问来源于stack exchange,提问作者Manu Tyagi
相关产品推荐
相关产品推荐

