Azure AAD - 受众群体无效

Shi*_*uel 6 active-directory azure asp.net-web-api azure-active-directory asp.net-core-webapi

我创建了一个用azure活动目录保护的webapi.我现在需要测试它并尝试使用带有授权标头的fiddler.我正在尝试使用以下代码生成令牌.

Target obj = (Target)cmbTarget.SelectedItem;

AuthenticationResult authenticationResult;
string aadInstance = obj.AADInstance; // "https://login.windows.net/{0}";
string tenant = obj.Tenant; //"rudderless.onmicrosoft.com";
string apiResourceId = obj.ApiResourceId; //"15b4ac7f-23a8-4958-96a5-64159254690d";
string clientId = obj.ClientId; // "47cdc6c3-226a-4c38-b08e-055be8409056";

Uri redirectUri = new Uri(obj.RedirectUri); //new Uri("http://nativeclient");
string authority = string.Format(aadInstance, tenant);
authContext = new AuthenticationContext(authority);

authenticationResult = this.authContext.AcquireToken(apiResourceId, 
                            clientId, redirectUri, PromptBehavior.Always);

txtToken.Text = authenticationResult.AccessToken;
Clipboard.SetText($"Bearer {txtToken.Text}");
Run Code Online (Sandbox Code Playgroud)

我成功生成了令牌,当我使用令牌调用webapi时,它会抛出401消息

WWW-Authenticate:Bearer error ="invalid_token",error_description ="观众无效"

Tod*_*all 12

问题

执行此受保护的 Web API:代码配置文章中的说明后,我收到了一条类似于 OP 的错误消息:

WWW-Authenticate: Bearer error="invalid_token", error_description="观众无效"

问题原来是我的appsettings.json文件中的AzureAd > ClientId 设置。

解决方案

我更新了appsettings.json我的 ASP.NET Core Web API 应用程序的文件,以便 ClientId 设置使用在我的应用程序注册>“公开 API”部分下的 portal.Azure.com 中找到的“应用程序 ID URI”。

在此处输入图片说明

appsettings.json 中的部分类似于以下内容:

"AzureAd": {
    "Instance": "https://login.microsoftonline.com/",
    "TenantId": "XXXXXXXX-XXXXX-XXXXX-XXXXX-XXXXXXXXXX",
    // ClientId = Portal.Azure.com > App Registration > Expose an API > "Application ID URI"
    "ClientId": "api://XXXXX-XXXXXX-XXXXX-XXXX-XXXXXXXXX"   
}
Run Code Online (Sandbox Code Playgroud)


小智 11

我遇到过同样的问题。想到了分享一下。我已将 Web Api Audience 更改为 Web 应用程序的 ClientId。在此之后它就起作用了。

Microsoft参考文献显示了以下示例:

{
  "AzureAd": {
    "Instance": "https://login.microsoftonline.com/",
    "ClientId": "[Client_id-of-web-api-eg-2ec40e65-ba09-4853-bcde-bcb60029e596]",
    "TenantId": "common",
    "Audience": "custom App ID URI for your web API"
  },
  // more lines
}
Run Code Online (Sandbox Code Playgroud)

  • 你能告诉我你到底在哪里做的吗? (16认同)
  • @Ron16 它位于 appsettings.json 中。如果您已将访问令牌接受版本设置为 2,或者对于 Azure AD B2C Web API,则客户端 ID 和受众需要相同(即无需编写 api://)源:https://learn.microsoft。 com/en-us/azure/active-directory/develop/scenario-protected-web-api-app-configuration (3认同)

Sha*_*izi 8

我认为重新审视身份验证的不同步骤很重要,希望通过讨论可以解决您遇到的问题。

当客户端试图获取对资源的访问令牌时,它需要向AAD指定要为其获取令牌的资源。客户端可能被配置为调用多个资源,而所有资源都具有不同的配置,因此可以期望总是在访问令牌请求中指定资源。

资源可以是资源的应用程序ID GUID,也可以是在资源上注册的有效应用程序ID URI。AAD应该能够根据您提供的价值来唯一标识要尝试获取的资源。但是,请注意,如果您使用App ID GUID,则会从AAD获得令牌,其中受众声明是App ID GUID。另外,如果您使用应用程序ID URI,您将在令牌中看到该URI作为受众声明。

在这两种情况下,您都将获得“相同”资源的令牌,但是令牌中的声明将以不同的方式出现。此外,单个应用程序资源可能在其应用程序上注册了多个应用程序ID URI。根据您在身份验证请求中使用的身份,您会在令牌中获得与您传入的资源参数匹配的其他受众声明。

最后,一旦获得令牌,就将其发送到Resource API,后者将对令牌进行多种验证,例如:客户ID声明,范围/角色声明,身份验证方法(“ acr”声明) ,而且观众的主张肯定符合他们的期望!

这意味着Resource API最终需要说“我接受<应用程序ID GUID>作为有效的受众声明” ...或“我接受<应用程序ID URI>作为有效的受众声明”。这种逻辑可能内置于您正在使用的库中(例如OWIN),但是您需要确保在API方面,已针对期望的受众正确配置了它。如果需要,可以这样做,以使您的API完全不检查Audience声明!令牌中的所有声明都是纯文本的,因此您确实可以做任何您想做的事,但是在那种情况下您将没有一个非常安全的API:]

归根结底,我的直觉是该错误来自您自己的API,并且正在发生,因为您尚未将您的应用配置为接受与您的资源的应用ID GUID相匹配的受众声明(看起来像您正在传递的内容)根据代码示例获取令牌时)。

希望这能解决您的问题!


小智 5

重要的提示

azure 为 JWT 令牌生成的“aud”值也由 AD 应用程序清单中的“accessTokenAcceptedVersion”属性控制。

此属性定义将生成的访问令牌的版本(有关 accessTokenAcceptedVersion 的 MS 文档)。

其值的可能结果:

  • null 或 1 - "api://" 前置到 GUID
  • 2 - 没有添加“api://”,所以应该只有 GUID


小智 5

也可能是您的应用程序/lib 使用的是较新版本的 api。如果应用程序清单中的 accessTokenAcceptedVersion 为 null,则 ms 默认为 v1。在http://jwt.io检查您的 jwt 令牌 如果您收到此消息 - 请检查您的 JWT 令牌。如果国际空间站不是这样

 "iss": "https://login.microsoftonline.com/[yadyada]/v2.0",
Run Code Online (Sandbox Code Playgroud)

那么很可能您正在使用另一个版本(例如默认版本 1)。检查您的 Azure 广告应用程序的清单:以下值可能为 null 或 1,应该为 2:

"accessTokenAcceptedVersion": 2,
Run Code Online (Sandbox Code Playgroud)