【问题标题】:Postman cannot access AAD protected Asp.net core 3.1 restapi. 401 unauthorizedPostman 无法访问受 AAD 保护的 Asp.net core 3.1 restapi。 401未经授权
【发布时间】:2020-04-23 17:35:09
【问题描述】:

我已通过以下步骤设置了受 AAD 保护的 asp.net core 3.1 restapi Web 服务。

  1. 注册一个服务器应用程序 (HelloWorld),然后添加一个范围。

  2. 注册一个客户端应用程序(domino-client)并创建一个秘密。然后添加服务器应用权限。

  3. 将 AAD 身份验证添加到 asp.net 核心。我创建了一个 rest api 项目并进行了以下更改。 (配置认证相关的服务和中间件。配置控制器。)

        public void ConfigureServices(IServiceCollection services)
        {
            services.AddControllers();

            services.AddAuthentication(o =>
            {
                o.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;
            })
            .AddJwtBearer(o =>
            {
                o.Authority = "https://login.microsoftonline.com/{tenant_id}";
                o.Audience = "a1faffea-24c6-42ff-9586-ee86ec7b8e80";          // server app client id
            });
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }

            app.UseHttpsRedirection();

            app.UseRouting();

            app.UseAuthentication();  // Add aad auth.

            app.UseAuthorization();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
            });
        }
    [Authorize]  // Enable auth.
    [ApiController]
    [Route("[controller]")]
    public class WeatherForecastController : ControllerBase
    {
        private static readonly string[] Summaries = new[]
        {
            "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
        };

        private readonly ILogger<WeatherForecastController> _logger;

        public WeatherForecastController(ILogger<WeatherForecastController> logger)
        {
            _logger = logger;
        }

        [HttpGet]
        public IEnumerable<WeatherForecast> Get()
        {
          .....
        }
    }

  1. 然后尝试使用postman访问api。

访问令牌时的一些参数。

  • 访问令牌网址:来自Endpoint
  • 客户端 ID:客户端应用程序客户端 ID
  • 客户端密码:客户端应用密码
  • 范围:服务器应用范围

Howerer,我收到 401 未经授权的错误。流程有问题吗?

【问题讨论】:

    标签: asp.net-core asp.net-web-api azure-active-directory


    【解决方案1】:

    根据您提供的详细信息,您希望使用OAuth 2.0 client credentials flow 访问受 Azure AD 保护的 API。如果是这样,您需要在服务器应用程序中定义 app role 而不是范围。

    具体步骤如下

    1. 创建服务器应用

    2. 定义应用角色

      一个。选择您要在其中定义应用角色的应用。然后选择Manifest

      b.通过找到 appRoles 设置并添加所有应用程序角色来编辑应用程序清单。应该是这样的

      "appRoles": [
      {
      "allowedMemberTypes": [
        "Application"
      ],
      "displayName": "access the web api",
      "id": "47fbb575-859a-4941-89c9-0f7a6c30beac",
      "isEnabled": true,
      "description": "Consumer apps have access to web api.",
      "value": "Consumer"
      }
      ],
      
    3. 注册客户端应用程序并创建密钥。

    4. 为您的客户端应用程序添加应用角色

    5. 配置网络 API

      一个。启动.cs

      public void ConfigureServices(IServiceCollection services)
        {
      services.AddAuthentication(x =>
            {
                x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
            })
          .AddJwtBearer(x =>
          {
              x.Authority = "https://login.microsoftonline.com/<tenant id>/v2.0";
              x.TokenValidationParameters = new TokenValidationParameters
              {
      
                  ValidateIssuer = false,
                   ValidAudiences = new[] {"<app id>","<app id url>" }
              };
          });
            services.AddControllers();
        }
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }
      
            app.UseHttpsRedirection();
      
            app.UseRouting();
      
            app.UseAuthentication();
            app.UseAuthorization();
      
            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
            });
        }
      

      b.在您的 API 控制器中添加 [Authorize] 以启用身份验证

    6. 在邮递员中测试

      一个。获取访问令牌

      b.调用接口

    【讨论】:

    • 非常感谢。我发现我误操作了邮递员。当我将“添加授权数据”从“请求URL”更改为“请求标头”时,我可以成功获取api。
    【解决方案2】:

    您正在使用 client credential flow 访问受保护的 Web api,访问令牌的受众是 api://fxxxb30-xxx-xxx-xxxx-bcaae52203cf,因此请尝试将您的 AddJwtBearer 选项修改为(另请注意您使用的是 Azure AD V2.0 端点):

    .AddJwtBearer(o =>
     {
         o.Authority = "https://login.microsoftonline.com/{tenant_id}/v2.0"; <--AAD V2.0
         o.Audience = "api://a1faffea-24c6-42ff-9586-ee86ec7b8e80";   <--  add api//     
     });
    

    另一个问题是您正在添加委托权限,因此客户端凭据流发出的访问令牌将不包含委托权限,而是您应该使用像 authorization code flow 这样的委托流。

    【讨论】:

      猜你喜欢
      • 2020-10-30
      • 1970-01-01
      • 1970-01-01
      • 2017-07-16
      • 1970-01-01
      • 1970-01-01
      • 2018-02-04
      • 2021-02-02
      • 1970-01-01
      相关资源
      最近更新 更多