node.js - 范围/角色声明在客户端凭据访问 token 中不可用

标签 node.js azure-active-directory microsoft-graph-api

login.microsoftonline.com/common/oauth2/v2.0/token 获取 access_token (grant_type=client_credentials) 后,我回来了:

HTTP 403
{
  "error": {
    "code": "AccessDenied",
    "message": "Either scp or roles claim need to be present in the token.",
    "innerError": {
      "request-id": "fa788422-6868-4ab3-9ded-5f076138bda2",
      "date": "2019-04-02T11:24:30"
    }
  }
}

当我 decoded the token ,它的主体中实际上没有 SCPROLES 键(与我从 Graph Explorer 读取的 token 中看到的相反)

我阅读了很多关于此的文档/博客,它们都指出添加“Microsoft Graph 的应用程序权限”,然后获得管理员同意。添加所需权限(Files.ReadWrite.AllFiles.ReadWrite.AppFolder 等)后,我获得了同意:

Admin consent on required permissions

代码:

const escapedScopeUri = querystring.escape(
  `https://graph.microsoft.com/.default`
);
const secretKey = querystring.escape(
  azureApplicationConfig.clientSecret
);
const requestBody = `client_id=${azureApplicationConfig.clientID}&client_secret=${secretKey}&scope=${escapedScopeUri}&grant_type=client_credentials`;

const authReqOptions = {
  method: `POST`,
  uri: `https://login.microsoftonline.com/common/oauth2/v2.0/token`,
  body: requestBody,
  headers: {
    "Content-Type": `application/x-www-form-urlencoded`
  }
};

rp(authReqOptions) // rp = request-promise module
  .then(async authRes => {
    console.log(authRes);
  })
  .catch(err => {
    // do something with err
  });

现在,这不是完整的代码,但它应该可以让您了解正在做什么。

在 authRes 可用后,我解码了 token 信息(范围不可用)。这是返回的信息:

{
  "token_type": "Bearer",
  "expires_in": 3600,
  "ext_expires_in": 3600,
  "access_token": "returned token"
}

和解码后的 token 主体信息: decoded token body information

此外,我在 list 中添加了 appRoles (不确定这是否是正确的格式):

{
  //...
  "appRoles": [
    {
      "allowedMemberTypes": ["User"],
      "description": "Trying to make app as Reader",
      "displayName": "Reader",
      "id": "4e76a3f3-86c9-4186-aa1d-c22ccc167326",
      "isEnabled": true,
      "lang": null,
      "origin": "Application",
      "value": "reader"
    },
    {
      "allowedMemberTypes": ["User"],
      "description": "Trying to make app as Admin",
      "displayName": "Admin",
      "id": "f3f3b2f0-3203-45fa-89e0-17a9c9b4ee73",
      "isEnabled": true,
      "lang": null,
      "origin": "Application",
      "value": "admin"
    }
  ]
  //...
}

事情仍然没有解决。

最佳答案

您无法向 /common 租户请求客户端凭据。由于您没有提供电子邮件地址(就像使用授权码或隐式一样),AAD 无法发现您要为其获取 token 的租户。

您需要提供租户 URI (domain.onmicrosoft.com) 或 id(创建每个租户时向其颁发的 GUID):

const authReqOptions = {
  method: `POST`,
  uri: `https://login.microsoftonline.com/${your-tenant-uri-or-id}/oauth2/v2.0/token`,
  body: requestBody,
  headers: {
    "Content-Type": `application/x-www-form-urlencoded`
  }
};

关于node.js - 范围/角色声明在客户端凭据访问 token 中不可用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55474036/

相关文章:

Azure AD B2C LinkedIn 个人资料图片

c# - 如何将 Azure AD 身份验证添加到现有 .net 网站

Azure AD ClaimsMappingPolicy 声明条件

microsoft-graph-api - 请求 Microsoft Graph/users/me/sendMail 返回 404

azure-active-directory - Microsoft Graph读取日历或发送邮件时返回 "NoPermissionsInAccessToken"如何解决

azure - 如何在Microsoft graph api中识别事件属于哪个日历?

javascript - Angular 2 验证状态

javascript - Nestjs:将提供者注入(inject)到由关键字 new 创建的对象中

node.js - 监听 UNIX 域套接字的 WebSockets?

node.js - Sequelize : delete JSONB property (with PostgreSQL)