Microsoft Graph API 授权错误。无效的受众

问题描述 投票:0回答:1

我知道这是一个很长的问题,但如果有人能与我分享他们的想法或经验,我会非常感激,因为我已经在这个问题上呆了几天,尝试了很多东西。我有一个 asp net core 3.1 web API 应用程序和一个 ASP.NET Core 3.1 MVC 应用程序。

两者都已在Azure AD中注册。API 项目应该根据从 MVC 项目收到的请求有效载荷创建日历事件。我按照微软的说明,从 此链接

但是一旦API项目针对Microsoft Graph进行调用,就会出现以下错误而失败。

"code". "InvalidAuthenticationToken", "message": "InvalidAuthenticationToken", "message": "访问令牌验证失败。无效的受众。"。

我在这里放了最低限度的信息,以提供更多的信息,但整个样本可以从以下地方下载。上面的链接.

ASP.NET核心MVC Startup.cs:

services.AddAuthentication(sharedOptions =>
        {
            sharedOptions.DefaultScheme = CookieAuthenticationDefaults.AuthenticationScheme;
            sharedOptions.DefaultChallengeScheme = OpenIdConnectDefaults.AuthenticationScheme;
        })
       .AddAzureAd(options =>
       {
           Configuration.Bind("AzureAd", options);
           AzureAdOptions.Settings = options;
       })
       .AddCookie();

ASP.NET Core MVC项目 AddAzureAd 职能:

public static AuthenticationBuilder AddAzureAd(this AuthenticationBuilder builder, Action<AzureAdOptions> configureOptions)
{
    builder.Services.Configure(configureOptions);
    builder.Services.AddSingleton<IConfigureOptions<OpenIdConnectOptions>, ConfigureAzureOptions>();
    builder.AddOpenIdConnect();
    return builder;
}

ConfigureAzureOptions:

public void Configure(string name, OpenIdConnectOptions options)
{
    options.ClientId = _azureOptions.ClientId;
    options.Authority = _azureOptions.Authority;
    options.UseTokenLifetime = true;
    options.CallbackPath = _azureOptions.CallbackPath;
    options.RequireHttpsMetadata = false;
    options.ClientSecret = _azureOptions.ClientSecret;
    options.Resource = "https://graph.microsoft.com"; // AAD graph

    // Without overriding the response type (which by default is id_token), the OnAuthorizationCodeReceived event is not called.
    // but instead OnTokenValidated event is called. Here we request both so that OnTokenValidated is called first which 
    // ensures that context.Principal has a non-null value when OnAuthorizeationCodeReceived is called
    options.ResponseType = "id_token code";

    // Subscribing to the OIDC events
    options.Events.OnAuthorizationCodeReceived = OnAuthorizationCodeReceived;
    options.Events.OnAuthenticationFailed = OnAuthenticationFailed;
}

而这里是API项目中配置Azure选项的代码。

private class ConfigureAzureOptions : IConfigureNamedOptions<JwtBearerOptions>
{
    private readonly AzureAdOptions _azureOptions;

    public ConfigureAzureOptions(IOptions<AzureAdOptions> azureOptions)
    {
        _azureOptions = azureOptions.Value;
    }

    public void Configure(string name, JwtBearerOptions options)
    {
        // options.Audience = _azureOptions.ClientId;
        options.Authority = $"{_azureOptions.Instance}{_azureOptions.TenantId}";

        // The valid audiences are both the Client ID(options.Audience) and api://{ClientID}
        // --->>> I've changed this to also have "https://graph.micrososft.com" but no luck
        options.TokenValidationParameters.ValidAudiences = new string[] { _azureOptions.ClientId, $"api://{_azureOptions.ClientId}" }; // <<--- I've changed this to "https://graph.micrososft.com" but no luck

        // If you want to debug, or just understand the JwtBearer events, uncomment the following line of code
        // options.Events = JwtBearerMiddlewareDiagnostics.Subscribe(options.Events);
    }

    public void Configure(JwtBearerOptions options)
    {
        Configure(Options.DefaultName, options);
    }
}

这就是我如何从MVC项目中获得一个令牌--权限是api:/client_id。

string userObjectID = User.FindFirst("http://schemas.microsoft.com/identity/claims/objectidentifier")?.Value;
            //AuthenticationContext authContext = new AuthenticationContext(AzureAdOptions.Settings.Authority, new NaiveSessionCache(userObjectID, HttpContext.Session));
            AuthenticationContext authContext = new AuthenticationContext(AzureAdOptions.Settings.Authority);
            ClientCredential credential = new ClientCredential(AzureAdOptions.Settings.ClientId, AzureAdOptions.Settings.ClientSecret);

我很感激你在这方面的想法和经验 - 再次感谢你的时间。

c# asp.net azure oauth-2.0 microsoft-graph
1个回答
1
投票

看起来你的客户端应用程序正在获取一个Microsoft Graph API令牌。

options.Resource = "https://graph.microsoft.com"; 

一个访问令牌有一个受众(aud claim),它指定了它的API.你的客户端应用程序需要使用你的API的客户端ID或应用程序ID URI作为资源,这样你就得到了一个为你的API设计的访问令牌。

如果你需要多个API的令牌,你需要为AuthorizationCodeReceived设置一个事件监听器,并使用MSAL.NET来交换令牌的授权代码。我有一个示例应用程序可以做到这一点。https:/github.comjuunas11aspnetcore2aadauthblob97ef0d62297995c350f40515938f7976ab7a9de2Core2AadAuthStartup.cs#L58。.这个应用虽然使用.NET Core 2.2和ADAL,但使用MSAL的一般方法也会类似。

© www.soinside.com 2019 - 2024. All rights reserved.