无法从AAD获取承载令牌以使用Web API(Unable to get bearer token from AAD to consume Web API)

我正在尝试保护我的Web API应用程序,以便只有特定的用户和应用程序才能使用这些服务。 我遵循了许多不同的说明,这些说明表明我有以下代码进行身份验证(我已将其简化为可在控制台应用程序中轻松重现):

class Program { private const string ServicesClientId = "11111111-1111-1111-1111-111111111111"; private const string ClientId = "aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa"; private const string ClientKey = "abcdefghijklmnopqrstuvwxyz1234567890="; private const string AadLoginUri = "https://login.windows.net/{0}"; private const string TenantId = "example.onmicrosoft.com"; private static readonly string Authority = string.Format(CultureInfo.InvariantCulture, AadLoginUri, TenantId); static void Main(string[] args) { var clientCredential = new ClientCredential(ClientId, ClientKey); var context = new AuthenticationContext(Authority, false); // This line fails! var appAuthResult = context.AcquireToken(ServicesClientId, clientCredential); // AADSTS50105: Application 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa' is not // assigned to a role for the application '11111111-1111-1111-1111-111111111111'. var appAuthTokenProvider = new ApplicationTokenProvider(context, "https://example.azurewebsites.net", clientCredential, appAuthResult); var tokenCreds = new TokenCredentials(appAuthTokenProvider); Console.WriteLine(tokenCreds.ToString()); Console.ReadLine(); } }

因此,只要禁用了用户分配但是启用了用户分配的时刻(并且等待一分钟,因为即使它表示已成功启用它似乎没有立即生效),此代码也能很好地工作,但它失败了。

我收到以下错误:

AADSTS50105:应用程序'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa'未分配给应用程序'11111111-1111-1111-1111-111111111111'的角色。

我该怎么做才能让它发挥作用?

我已经尝试过各种各样的事情,以便在没有运气的情况下让它消失。 我尝试过的事情:

将我的注册客户端的默认“Access MyWebAPI”权限添加到已注册的Web API项目中 更改Web API应用程序的清单以添加App角色: { "allowedMemberTypes": [ "Application" ], "displayName": "Universal App Client", "id": "c27e3fa1-e96a-445c-aaf7-8cbb60cca980", "isEnabled": true, "description": "Application Consuming all Services.", "value": "AppClient" }然后设置应用程序权限(在已注册的消费应用程序上)以获得此新的“Universal App Client”权限。 更改Web API应用程序的清单,以在knownClientApplications数组下添加使用应用程序的客户端ID。 我已经多次重新配置了我的Web API应用程序,以防我通过故障排除过程进行了充实,但我总是最终完成 在揉我的肚子时拍拍我的头。

我不确定下一步该尝试什么。


出于参考目的,这是我的packages.config文件:

<?xml version="1.0" encoding="utf-8"?> <packages> <package id="Microsoft.IdentityModel.Clients.ActiveDirectory" version="2.28.1" targetFramework="net46" /> <package id="Microsoft.Rest.ClientRuntime" version="1.8.2" targetFramework="net46" /> <package id="Microsoft.Rest.ClientRuntime.Azure.Authentication" version="0.11.3" targetFramework="net46" /> <package id="Newtonsoft.Json" version="9.0.1" targetFramework="net46" /> </packages>

这个问题与其他问题类似,但如上所述,这个问题(重新配置和重新部署)的答案对我不起作用。

I am attempting to secure my Web API applications such that only specific users and applications can consume the services. I have followed many different instructions that have suggested that I have the following code to authenticate (I have simplified this to be easily reproducible in a Console application):

class Program { private const string ServicesClientId = "11111111-1111-1111-1111-111111111111"; private const string ClientId = "aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa"; private const string ClientKey = "abcdefghijklmnopqrstuvwxyz1234567890="; private const string AadLoginUri = "https://login.windows.net/{0}"; private const string TenantId = "example.onmicrosoft.com"; private static readonly string Authority = string.Format(CultureInfo.InvariantCulture, AadLoginUri, TenantId); static void Main(string[] args) { var clientCredential = new ClientCredential(ClientId, ClientKey); var context = new AuthenticationContext(Authority, false); // This line fails! var appAuthResult = context.AcquireToken(ServicesClientId, clientCredential); // AADSTS50105: Application 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa' is not // assigned to a role for the application '11111111-1111-1111-1111-111111111111'. var appAuthTokenProvider = new ApplicationTokenProvider(context, "https://example.azurewebsites.net", clientCredential, appAuthResult); var tokenCreds = new TokenCredentials(appAuthTokenProvider); Console.WriteLine(tokenCreds.ToString()); Console.ReadLine(); } }

So this code works beautifully as long as user assignment is disabled but the moment that user assignment is enabled (and you wait a minute as it doesn't appear to be effective instantly even though it says it was successfully enabled), it fails.

I receive the following error:

AADSTS50105: Application 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa' is not assigned to a role for the application '11111111-1111-1111-1111-111111111111'.

What must I do to get this to work?

I have tried and tried all sorts of things to get this to go away without luck. Things I have tried:

Adding the default "Access MyWebAPI" permission from my registered client to the registered Web API project Changing the manifest for the Web API application to add an App Role: { "allowedMemberTypes": [ "Application" ], "displayName": "Universal App Client", "id": "c27e3fa1-e96a-445c-aaf7-8cbb60cca980", "isEnabled": true, "description": "Application Consuming all Services.", "value": "AppClient" } and then setting the Application Permission (on the registered consuming application) to have this new "Universal App Client" permission. Changing the manifest for the Web API application to add the consuming application's Client ID under the knownClientApplications array. I have reprovisioned my Web API application several times in case I goofed it up via the troubleshooting process but I always end up Patting my head while rubbing my stomach.

I'm not sure what to try next.


For reference purposes, here is my packages.config file:

<?xml version="1.0" encoding="utf-8"?> <packages> <package id="Microsoft.IdentityModel.Clients.ActiveDirectory" version="2.28.1" targetFramework="net46" /> <package id="Microsoft.Rest.ClientRuntime" version="1.8.2" targetFramework="net46" /> <package id="Microsoft.Rest.ClientRuntime.Azure.Authentication" version="0.11.3" targetFramework="net46" /> <package id="Newtonsoft.Json" version="9.0.1" targetFramework="net46" /> </packages>

This question is similar to this other question but the answer to that question (reprovision & redeploy it) does not work for me, as mentioned above.

最满意答案

我也可以重现这个问题。 我发现当我向应用程序角色授予Web API时,该角色可能未按预期授予。 这是图供您参考: 在此处输入图像描述

作为限制用户和应用程序的解决方法,我们可以在Web API中对其进行编码,以便自己实现令牌处理程序。 例如,我们可以配置允许的用户,应用程序,然后解析访问令牌以检索appid和upn以验证它。 有关自定义令牌处理程序的更多细节,您可以参考此线程 。

对于原始问题,我也试图在内部报告。

I could reproduce this issue too. I found when I grant the application role the web API, the role maybe not granted as expected. Here is figure for your reference: enter image description here

As a workaround to limit the users and applications, we can code it in the web API to implement the token handler ourselves. For example, we can config the allowed users, applications and then parse the access token to retrieve the appid and upn to verify it. More detail about custom token handler, you can refer this thread.

And for the original issue, I am also trying to report it internally.

更多推荐