【问题标题】:Need to generate Azure AD bearer token using C# rest call需要使用 C# rest 调用生成 Azure AD 不记名令牌
【发布时间】:2018-05-24 13:58:21
【问题描述】:

我想通过 C# REST 调用生成 Azure AD 不记名令牌。我想在 API 调用中编写用户注册逻辑。我将其用作令牌端点:

https://login.windows.net/[tenant-id]/oauth2/token

我遵循了与this 文章中所述相同的程序。

我使用的用户凭据是“全局管理员”。

但我仍然收到“未经授权”错误。请在下面找到代码 sn-p 和响应正文-

代码

using (HttpClient client = new HttpClient())
        {
            var tokenEndpoint = @"https://login.windows.net/<tanent-name>/oauth2/token";
            var accept = "application/json";

            client.DefaultRequestHeaders.Add("Accept", accept);
            string postBody = @"resource=https%3A%2F%2Fgraph.microsoft.com%2F
              &client_id=<client-id>
              &grant_type=password
              &username=<admin-user-name>
              &password=<admin-pass>
              &scope=openid";

            using (var response = await client.PostAsync(tokenEndpoint, new StringContent(postBody, Encoding.UTF8, "application/x-www-form-urlencoded")))
            {
                if (response.IsSuccessStatusCode)
                {
                    var jsonresult = JObject.Parse(await response.Content.ReadAsStringAsync());
                    var token = (string)jsonresult["access_token"];
                    return token;
                }
                else
                    return null;
            }
        }

响应正文

{ StatusCode: 401, ReasonPhrase: 'Unauthorized',
  Version: 1.1, Content: System.Net.Http.StreamContent, Headers:
{
  Pragma: no-cache
  Strict-Transport-Security: max-age=31536000; includeSubDomains
  X-Content-Type-Options: nosniff
  x-ms-request-id: cabefe46-ff73-4659-80a2-2f4136200900
  Cache-Control: no-store, no-cache
  P3P: CP="DSP CUR OTPi IND OTRi ONL FIN"
  Set-Cookie: esctx=AQABAAAAAADX8GCi6Js6SK82TsD2Pb7...
  Set-Cookie: x-ms-gateway-slice=004; path=/; secure; HttpOnly
  Set-Cookie: stsservicecookie=ests; path=/; secure; HttpOnly
  Server: Microsoft-IIS/10.0
  X-Powered-By: ASP.NET
  Date: Thu, 24 May 2018 13:43:39 GMT
  Content-Length: 457
  Content-Type: application/json; charset=utf-8
  Expires: -1
}}

P.S.- 另外请指出是否有任何其他方法可以在不进行 REST 调用的情况下添加新用户。我不想在客户端应用程序中进行用户注册。

[更新]请查看添加权限和角色的截图。

【问题讨论】:

  • 不使用ADAL.NET的任何特殊原因?
  • 401 错误表示您无权执行此操作。您要访问哪个 API?您提到的link 是用于操作Microsoft Graph API。对于不同的 API,资源是不同的。有关您要操作哪个 API 的更多信息将更有帮助。
  • 由于您使用的是 ROPC 授权流程,该用户是该客户端(AAD 应用程序)的所有者吗?
  • 我正在尝试使用 Graph API 添加新用户。请查看更新的屏幕截图以了解添加的角色和权限。
  • 对。应该是login.microsoftonline.com。单击Step 6 中的授予同意按钮。我看到您正在使用应用程序权限,我认为密码流程不需要,很可能需要委派权限。要使用应用权限,您需要切换到客户端凭据流(应用 ID 和应用密码)。 ADAL 完全支持这一点。

标签: c# azure azure-active-directory bearer-token azure-security


【解决方案1】:

正如汤姆所说,您的问题应该是由于用户对您的应用没有权限引起的。

由于您使用的是 ROPC 授权流程,请确保用户是该客户端/AAD 应用程序的所有者。

您可以将 onwer 添加到 AAD 应用:

转到 Azure 门户 > Azure Acitve Directory > 应用程序注册 > 应用程序 > 设置 > 所有者 > 添加所有者 > 选择该用户。

另外,如果用户启用了 MFA,此流程将不起作用。

如果有帮助请告诉我!

【讨论】:

  • 嗨@Wayne,我已将此用户添加为应用程序的所有者。但它仍然给出同样的错误。请查找更新的屏幕截图以供参考。
  • 嗨@Sudip。你的 App 是什么类型的?
  • 我正在使用控制台应用程序 (.NET 4.6) 进行测试。稍后我会将代码移至 Web API 逻辑。
  • 嗯...你最好用Native app注册你的应用。
  • 好的..会试试看。我会及时通知你。
【解决方案2】:

另外请指出是否有任何其他方法可以在不进行 REST 调用的情况下添加新用户。我不想在客户端应用程序中进行用户注册。

如果您想创建用户,我们可以使用Microsoft.Graph 来执行此操作。

在此之前我们需要registry the Azure AD application。并添加 Microsoft graph 权限。更多详情可以参考Create User API。

我使用 Directory.ReadWrite.All 权限对其进行测试。不要忘记授予权限。

演示代码。

string graphResourceId = "https://graph.microsoft.com/";
string authority = "https://login.microsoftonline.com/{0}";
string tenantId = "tenant Id";
string clientId = "client Id";
string secret = "secret";
authority = String.Format(authority, tenantId);
AuthenticationContext authContext = new AuthenticationContext(authority);
var accessToken = authContext.AcquireTokenAsync(graphResourceId, new ClientCredential(clientId, secret)).Result.AccessToken;
            var graphserviceClient = new GraphServiceClient(
                new DelegateAuthenticationProvider(
                    requestMessage =>
                    {
                        requestMessage.Headers.Authorization = new AuthenticationHeaderValue("bearer", accessToken);

                        return Task.FromResult(0);
                    }));
var user = new User
         {
             UserPrincipalName = "tomaccount1@xxxxx.onmicrosoft.com",
             AccountEnabled = true,
             DisplayName = "tom1",
             PasswordProfile = new PasswordProfile
             {
                 ForceChangePasswordNextSignIn = true,
                 Password = "1234qweA!@#$%6"
             },
              MailNickname = "tomaccount1"
            };
 var addUserResult = graphserviceClient.Users.Request().AddAsync(user).Result;

测试结果:

从 Azure AD 检查

Packages.config

<?xml version="1.0" encoding="utf-8"?>
<packages>
  <package id="Microsoft.Graph" version="1.9.0" targetFramework="net471" />
  <package id="Microsoft.Graph.Core" version="1.9.0" targetFramework="net471" />
  <package id="Microsoft.IdentityModel.Clients.ActiveDirectory" version="3.19.4" targetFramework="net471" />
  <package id="Newtonsoft.Json" version="11.0.2" targetFramework="net471" />
  <package id="System.IO" version="4.3.0" targetFramework="net471" />
  <package id="System.Net.Http" version="4.3.3" targetFramework="net471" />
  <package id="System.Runtime" version="4.3.0" targetFramework="net471" />
  <package id="System.Security.Cryptography.Algorithms" version="4.3.1" targetFramework="net471" />
  <package id="System.Security.Cryptography.Encoding" version="4.3.0" targetFramework="net471" />
  <package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="net471" />
  <package id="System.Security.Cryptography.X509Certificates" version="4.3.2" targetFramework="net471" />
</packages>

【讨论】:

  • 谢谢,但现在有点卡住了。一定会试试这个,并随时通知您。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-10-07
  • 2021-07-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多