Использование API Graph в ASP.NET Core Blazor WebAssembly

Примечание.

Это не последняя версия этой статьи. В текущем выпуске см . версию .NET 8 этой статьи.

Внимание

Эта информация относится к предварительному выпуску продукта, который может быть существенно изменен до его коммерческого выпуска. Майкрософт не предоставляет никаких гарантий, явных или подразумеваемых, относительно приведенных здесь сведений.

В текущем выпуске см . версию .NET 8 этой статьи.

В этой статье объясняется, как использовать API Microsoft Graph в Blazor WebAssembly приложениях, который является RESTful web API, который позволяет приложениям получать доступ к ресурсам службы Microsoft Cloud.

Два подхода доступны для прямого взаимодействия с Microsoft Graph в Blazor приложениях:

  • Пакет SDK Graph. Пакеты SDK Microsoft Graph предназначены для упрощения создания высококачественных, эффективных и устойчивых приложений, обращаюющихся к Microsoft Graph. Нажмите кнопку SDK Graph в верхней части этой статьи, чтобы применить этот подход.

  • Именованный HttpClient с API Graph: именованный HttpClientможет выдавать запросы веб-API непосредственно к API Graph. Нажмите кнопку "Именованный HttpClient" с помощью API Graph в верхней части этой статьи, чтобы применить этот подход.

Рекомендации в этой статье не предназначены для замены основной документации Microsoft Graph и дополнительных рекомендаций по безопасности Azure в других наборах документации Майкрософт. Оцените рекомендации по безопасности в разделе "Дополнительные ресурсы " этой статьи перед реализацией Microsoft Graph в рабочей среде. Следуйте всем рекомендациям Корпорации Майкрософт, чтобы ограничить область области атаки ваших приложений.

Внимание

Сценарии, описанные в этой статье, относятся к использованию Microsoft Entra (ME-ID) в качестве поставщика удостоверений, а не AAD B2C. Использование Microsoft Graph с клиентским Blazor WebAssembly приложением и поставщиком удостоверений AAD B2C на данный момент не поддерживается, так как приложению потребуется секрет клиента, который не может быть защищен в клиентском Blazor приложении. Для автономного Blazor WebAssembly приложения AAD B2C используйте API Graph, создайте внутренний API сервера (веб-) для доступа к API Graph от имени пользователей. Клиентское приложение выполняет проверку подлинности и разрешает пользователям вызывать веб-API для безопасного доступа к Microsoft Graph и возврата данных клиентскому Blazor приложению. Секрет клиента безопасно сохраняется в веб-API на основе сервера, а не в Blazor приложении на клиенте. Никогда не храните секрет клиента в клиентском Blazor приложении.

Использование размещенного Blazor WebAssembly приложения поддерживается, где Server приложение использует пакет SDK или API Graph для предоставления данных Graph приложению Client через веб-API. Дополнительные сведения см. в разделе "Размещенные Blazor WebAssembly решения " этой статьи.

Примеры, приведенные в этой статье, используют новые функции .NET/C#. При использовании примеров с .NET 7 или более ранней версией требуются незначительные изменения. Однако примеры текста и кода, относящиеся к взаимодействию с Microsoft Graph, одинаковы для всех версий ASP.NET Core.

Следующее руководство относится к Microsoft Graph версии 5.

Пакет SDK Microsoft Graph для использования в Blazor приложениях называется клиентской библиотекой Microsoft Graph .NET.

В примерах пакета SDK Graph требуются следующие ссылки на пакеты в автономном Blazor WebAssembly приложении. На первые два пакета уже ссылается, если приложение было включено для проверки подлинности MSAL, например при создании приложения, следуя инструкциям в разделе "Защита автономного приложения ASP.NET CoreBlazor WebAssembly" с помощью идентификатора Microsoft Entra.

В примерах пакета SDK Graph требуются следующие ссылки на пакеты в автономном Blazor WebAssembly приложении или Client приложении размещенного Blazor WebAssembly решения. На первые два пакета уже ссылается, если приложение было включено для проверки подлинности MSAL, например при создании приложения, следуя инструкциям в разделе "Защита автономного приложения ASP.NET CoreBlazor WebAssembly" с помощью идентификатора Microsoft Entra.

Примечание.

Рекомендации по добавлению пакетов в приложения .NET см. в разделе Способы установки пакетов NuGet в статье Рабочий процесс использования пакета (документация по NuGet). Проверьте правильность версий пакета на сайте NuGet.org.

В портал Azure предоставьте делегированные разрешения (область)† для данных Microsoft Graph, к которым приложение должно иметь доступ от имени пользователя. Например, в этой статье регистрация приложения должна включать делегированное разрешение на чтение данных пользователя (Microsoft.Graph>User.Readобласть в разрешениях API, Тип: Делегировано). Область User.Read позволяет пользователям входить в приложение и позволяет приложению читать сведения о профиле и компании пользователей, вошедшего в систему. Дополнительные сведения см. в разделе "Обзор разрешений и согласия" в платформа удостоверений Майкрософт и обзоре разрешений Microsoft Graph.

Примечание.

†Permissions и область означает то же самое и используется взаимозаменяемо в документации по безопасности и портал Azure. В этой статье используются область/ область при обращении к разрешениям API Graph.

После добавления api Microsoft Graph область в регистрацию приложения в портал Azure добавьте в файл в приложении следующую конфигурацию wwwroot/appsettings.json параметров приложения, которая включает базовый URL-адрес Graph с версией Microsoft Graph и область. В следующем примере User.Read область указывается для примеров в последующих разделах этой статьи. Области не учитывает регистр.

"MicrosoftGraph": {
  "BaseUrl": "https://graph.microsoft.com/{VERSION}/",
  "Scopes": [
    "user.read"
  ]
}

В предыдущем примере заполнитель — это версия API Microsoft Graph (например: {VERSION}v1.0). Косая черта требуется.

Ниже приведен пример полного wwwroot/appsettings.json файла конфигурации для приложения, использующего ME-ID в качестве поставщика удостоверений, где для Microsoft Graph указывается чтение пользовательских данных (user.readобласть).

{
  "AzureAd": {
    "Authority": "https://login.microsoftonline.com/{TENANT ID}",
    "ClientId": "{CLIENT ID}",
    "ValidateAuthority": true
  },
  "MicrosoftGraph": {
    "BaseUrl": "https://graph.microsoft.com/v1.0/",
    "Scopes": [
      "user.read"
    ]
  }
}

В предыдущем примере {TENANT ID} заполнитель — это идентификатор каталога (клиента), а {CLIENT ID} заполнитель — идентификатор приложения (клиента). Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Добавьте следующий GraphClientExtensions класс в автономное приложение. Область предоставляются Scopes свойству AccessTokenRequestOptions методаAuthenticateRequestAsync.

Добавьте следующий класс GraphClientExtensions в изолированное приложение или приложение Client размещенного Blazor WebAssemblyрешения . Область предоставляются Scopes свойству AccessTokenRequestOptions методаAuthenticateRequestAsync.

Если маркер доступа не получен, следующий код не задает заголовок авторизации носителя для запросов Graph.

GraphClientExtensions.cs:

using Microsoft.AspNetCore.Components.WebAssembly.Authentication;
using Microsoft.Authentication.WebAssembly.Msal.Models;
using Microsoft.Graph;
using Microsoft.Kiota.Abstractions;
using Microsoft.Kiota.Abstractions.Authentication;
using IAccessTokenProvider = 
    Microsoft.AspNetCore.Components.WebAssembly.Authentication.IAccessTokenProvider;

namespace BlazorSample;

internal static class GraphClientExtensions
{
    public static IServiceCollection AddGraphClient(
            this IServiceCollection services, string? baseUrl, List<string>? scopes)
    {
        if (string.IsNullOrEmpty(baseUrl) || scopes?.Count == 0)
        {
            return services;
        }

        services.Configure<RemoteAuthenticationOptions<MsalProviderOptions>>(
            options =>
            {
                scopes?.ForEach((scope) =>
                {
                    options.ProviderOptions.DefaultAccessTokenScopes.Add(scope);
                });
            });

        services.AddScoped<IAuthenticationProvider, GraphAuthenticationProvider>();

        services.AddScoped(sp =>
        {
            return new GraphServiceClient(
                new HttpClient(),
                sp.GetRequiredService<IAuthenticationProvider>(),
                baseUrl);
        });

        return services;
    }

    private class GraphAuthenticationProvider(IAccessTokenProvider tokenProvider, 
        IConfiguration config) : IAuthenticationProvider
    {
        private readonly IConfiguration config = config;

        public IAccessTokenProvider TokenProvider { get; } = tokenProvider;

        public async Task AuthenticateRequestAsync(RequestInformation request, 
            Dictionary<string, object>? additionalAuthenticationContext = null, 
            CancellationToken cancellationToken = default)
        {
            var result = await TokenProvider.RequestAccessToken(
                new AccessTokenRequestOptions()
                {
                    Scopes = 
                        config.GetSection("MicrosoftGraph:Scopes").Get<string[]>()
                });

            if (result.TryGetToken(out var token))
            {
                request.Headers.Add("Authorization", 
                    $"{CoreConstants.Headers.Bearer} {token.Value}");
            }
        }
    }
}

Внимание

AdditionalScopesToConsentDefaultAccessTokenScopes Дополнительные сведения о том, почему предыдущий код использует DefaultAccessTokenScopes для добавления область вместо AdditionalScopesToConsentраздела .

В файле добавьте клиентские Program службы Graph и конфигурацию с AddGraphClient помощью метода расширения:

var baseUrl = builder.Configuration.GetSection("MicrosoftGraph")["BaseUrl"];
var scopes = builder.Configuration.GetSection("MicrosoftGraph:Scopes")
    .Get<List<string>>();

builder.Services.AddGraphClient(baseUrl, scopes);

Вызов API Graph из компонента с помощью пакета SDK для Graph

UserData Следующий компонент использует внедренный GraphServiceClient объект для получения данных профиля ME-ID пользователя и отображения номера мобильного телефона.

Для любого тестового пользователя, который вы создаете в ME-ID, убедитесь, что вы предоставите профилю ME-ID пользователя номер мобильного телефона в портал Azure.

UserData.razor:

@page "/user-data"
@using Microsoft.AspNetCore.Authorization
@using Microsoft.Graph
@attribute [Authorize]
@inject GraphServiceClient Client

<PageTitle>User Data</PageTitle>

<h1>Microsoft Graph User Data</h1>

@if (!string.IsNullOrEmpty(user?.MobilePhone))
{
    <p>Mobile Phone: @user.MobilePhone</p>
}

@code {
    private Microsoft.Graph.Models.User? user;

    protected override async Task OnInitializedAsync()
    {
        user = await Client.Me.GetAsync();
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-data">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Data
    </NavLink>
</div>

Совет

Сведения о добавлении пользователей в приложение см. в разделе "Назначение пользователей регистрации приложения" с ролями приложений или без нее.

При локальном тестировании с помощью пакета SDK Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieпомехи тестам. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Настройка утверждений пользователей с помощью пакета SDK Graph

В следующем примере приложение создает мобильный номер телефона и утверждения о расположении офиса для пользователя из данных профиля пользователя ME-ID. Приложение должно иметь API Graph, область настроенный User.Read в ME-ID. Все тестовые пользователи для этого сценария должны иметь номер мобильного телефона и офис в своем профиле ME-ID, который можно добавить через портал Azure.

В следующей фабрике пользовательских учетных записей пользователей:

  • Значение (ILoggerlogger) включается для удобства, если вы хотите регистрировать сведения или ошибки в методеCreateUserAsync.
  • AccessTokenNotAvailableException При возникновении ошибки пользователь перенаправляется в поставщик удостоверений для входа в учетную запись. При запросе маркера доступа могут выполняться дополнительные или различные действия. Например, приложение может записать AccessTokenNotAvailableException и создать запрос в службу поддержки для дальнейшего изучения.
  • RemoteUserAccount Платформа представляет учетную запись пользователя. Если приложению требуется пользовательский класс учетной записи пользователя, который расширяется RemoteUserAccount, переключите класс пользовательской учетной записи пользователя на RemoteUserAccount следующий код.

CustomAccountFactory.cs:

using System.Security.Claims;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication.Internal;
using Microsoft.Graph;
using Microsoft.Kiota.Abstractions.Authentication;

namespace BlazorSample;

public class CustomAccountFactory(IAccessTokenProviderAccessor accessor,
        IServiceProvider serviceProvider, ILogger<CustomAccountFactory> logger,
        IConfiguration config) 
    : AccountClaimsPrincipalFactory<RemoteUserAccount>(accessor)
{
    private readonly ILogger<CustomAccountFactory> logger = logger;
    private readonly IServiceProvider serviceProvider = serviceProvider;
    private readonly string? baseUrl = 
        config.GetSection("MicrosoftGraph")["BaseUrl"];

    public override async ValueTask<ClaimsPrincipal> CreateUserAsync(
        RemoteUserAccount account,
        RemoteAuthenticationUserOptions options)
    {
        var initialUser = await base.CreateUserAsync(account, options);

        if (initialUser.Identity is not null &&
            initialUser.Identity.IsAuthenticated)
        {
            var userIdentity = initialUser.Identity as ClaimsIdentity;

            if (userIdentity is not null && !string.IsNullOrEmpty(baseUrl))
            {
                try
                {
                    var client = new GraphServiceClient(
                        new HttpClient(),
                        serviceProvider
                            .GetRequiredService<IAuthenticationProvider>(),
                        baseUrl);

                    var user = await client.Me.GetAsync();

                    if (user is not null)
                    {
                        userIdentity.AddClaim(new Claim("mobilephone",
                            user.MobilePhone ?? "(000) 000-0000"));
                        userIdentity.AddClaim(new Claim("officelocation",
                            user.OfficeLocation ?? "Not set"));
                    }
                }
                catch (AccessTokenNotAvailableException exception)
                {
                    exception.Redirect();
                }
            }
        }

        return initialUser;
    }
}

Настройте проверку подлинности MSAL для использования фабрики пользовательских учетных записей пользователей.

Убедитесь, что Program файл использует Microsoft.AspNetCore.Components.WebAssembly.Authentication пространство имен:

using Microsoft.AspNetCore.Components.WebAssembly.Authentication;

Пример в этом разделе основан на подходе чтения базового URL-адреса с версией и область из конфигурации приложения с помощью MicrosoftGraph раздела в wwwroot/appsettings.json файле. Следующие строки уже должны присутствовать в Program файле, следуя инструкциям, приведенным ранее в этой статье:

var baseUrl = builder.Configuration.GetSection("MicrosoftGraph")["BaseUrl"];
var scopes = builder.Configuration.GetSection("MicrosoftGraph:Scopes")
    .Get<List<string>>();

builder.Services.AddGraphClient(baseUrl, scopes);

Program В файле найдите вызов AddMsalAuthentication метода расширения. Обновите код до следующего, включив вызов, который AddAccountClaimsPrincipalFactory добавляет фабрику субъектов утверждений учетной записи с помощью CustomAccountFactory.

Если приложение использует пользовательский класс учетной записи пользователя, RemoteUserAccountрасширяющийся, переключите класс пользовательской учетной записи пользователя на RemoteUserAccount следующий код.

builder.Services.AddMsalAuthentication<RemoteAuthenticationState,
    RemoteUserAccount>(options =>
    {
        builder.Configuration.Bind("AzureAd", 
            options.ProviderOptions.Authentication);
    })
    .AddAccountClaimsPrincipalFactory<RemoteAuthenticationState, RemoteUserAccount,
        CustomAccountFactory>();

Чтобы изучить утверждения пользователя после проверки подлинности пользователя с помощью ME-ID, можно использовать следующий UserClaims компонент:

UserClaims.razor:

@page "/user-claims"
@using System.Security.Claims
@using Microsoft.AspNetCore.Authorization
@attribute [Authorize]
@inject AuthenticationStateProvider AuthenticationStateProvider

<h1>User Claims</h1>

@if (claims.Any())
{
    <ul>
        @foreach (var claim in claims)
        {
            <li>@claim.Type: @claim.Value</li>
        }
    </ul>
}
else
{
    <p>No claims found.</p>
}

@code {
    private IEnumerable<Claim> claims = Enumerable.Empty<Claim>();

    protected override async Task OnInitializedAsync()
    {
        var authState = await AuthenticationStateProvider
            .GetAuthenticationStateAsync();
        var user = authState.User;

        claims = user.Claims;
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-claims">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Claims
    </NavLink>
</div>

При локальном тестировании с помощью пакета SDK Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieпомехи тестам. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Следующее руководство относится к Microsoft Graph версии 4. Если вы обновляете приложение из пакета SDK версии 4 до версии 5, ознакомьтесь с руководством по изменению и обновлению пакета SDK для Microsoft Graph для .NET версии 5.

Пакет SDK Microsoft Graph для использования в Blazor приложениях называется клиентской библиотекой Microsoft Graph .NET.

В примерах пакета SDK Graph требуются следующие ссылки на пакеты в автономном Blazor WebAssembly приложении. На первые два пакета уже ссылается, если приложение было включено для проверки подлинности MSAL, например при создании приложения, следуя инструкциям в разделе "Защита автономного приложения ASP.NET CoreBlazor WebAssembly" с помощью идентификатора Microsoft Entra.

В примерах пакета SDK Graph требуются следующие ссылки на пакеты в автономном Blazor WebAssembly приложении или Client приложении размещенного Blazor WebAssembly решения. На первые два пакета уже ссылается, если приложение было включено для проверки подлинности MSAL, например при создании приложения, следуя инструкциям в разделе "Защита автономного приложения ASP.NET CoreBlazor WebAssembly" с помощью идентификатора Microsoft Entra.

Примечание.

Рекомендации по добавлению пакетов в приложения .NET см. в разделе Способы установки пакетов NuGet в статье Рабочий процесс использования пакета (документация по NuGet). Проверьте правильность версий пакета на сайте NuGet.org.

В портал Azure предоставьте делегированные разрешения (область)† для данных Microsoft Graph, к которым приложение должно иметь доступ от имени пользователя. Например, в этой статье регистрация приложения должна включать делегированное разрешение на чтение данных пользователя (Microsoft.Graph>User.Readобласть в разрешениях API, Тип: Делегировано). Область User.Read позволяет пользователям входить в приложение и позволяет приложению читать сведения о профиле и компании пользователей, вошедшего в систему. Дополнительные сведения см. в разделе "Обзор разрешений и согласия" в платформа удостоверений Майкрософт и обзоре разрешений Microsoft Graph.

Примечание.

†Permissions и область означает то же самое и используется взаимозаменяемо в документации по безопасности и портал Azure. В этой статье используются область/ область при обращении к разрешениям API Graph.

После добавления api Microsoft Graph область в регистрацию приложения в портал Azure добавьте в файл в приложении следующую конфигурацию wwwroot/appsettings.json параметров приложения, которая включает базовый URL-адрес Graph с версией Microsoft Graph и область. В следующем примере User.Read область указывается для примеров в последующих разделах этой статьи. Области не учитывает регистр.

"MicrosoftGraph": {
  "BaseUrl": "https://graph.microsoft.com/{VERSION}/",
  "Scopes": [
    "user.read"
  ]
}

В предыдущем примере заполнитель — это версия API Microsoft Graph (например: {VERSION}v1.0). Косая черта требуется.

Ниже приведен пример полного wwwroot/appsettings.json файла конфигурации для приложения, использующего ME-ID в качестве поставщика удостоверений, где для Microsoft Graph указывается чтение пользовательских данных (user.readобласть).

{
  "AzureAd": {
    "Authority": "https://login.microsoftonline.com/{TENANT ID}",
    "ClientId": "{CLIENT ID}",
    "ValidateAuthority": true
  },
  "MicrosoftGraph": {
    "BaseUrl": "https://graph.microsoft.com/v1.0/",
    "Scopes": [
      "user.read"
    ]
  }
}

В предыдущем примере {TENANT ID} заполнитель — это идентификатор каталога (клиента), а {CLIENT ID} заполнитель — идентификатор приложения (клиента). Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Добавьте следующий GraphClientExtensions класс в автономное приложение. Область предоставляются Scopes свойству AccessTokenRequestOptions методаAuthenticateRequestAsync. Значение IHttpProvider.OverallTimeout по умолчанию расширено от 100 секунд до 300 секунд, чтобы получить HttpClient больше времени для получения ответа от Microsoft Graph.

Добавьте следующий класс GraphClientExtensions в изолированное приложение или приложение Client размещенного Blazor WebAssemblyрешения . Область предоставляются Scopes свойству AccessTokenRequestOptions методаAuthenticateRequestAsync. Значение IHttpProvider.OverallTimeout по умолчанию расширено от 100 секунд до 300 секунд, чтобы получить HttpClient больше времени для получения ответа от Microsoft Graph.

Если маркер доступа не получен, следующий код не задает заголовок авторизации носителя для запросов Graph.

GraphClientExtensions.cs:

using System.Net.Http.Headers;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication;
using Microsoft.Authentication.WebAssembly.Msal.Models;
using Microsoft.Graph;

namespace BlazorSample;

internal static class GraphClientExtensions
{
    public static IServiceCollection AddGraphClient(
        this IServiceCollection services, string? baseUrl, List<string>? scopes)
    {
        if (string.IsNullOrEmpty(baseUrl) || scopes?.Count == 0)
        {
            return services;
        }

        services.Configure<RemoteAuthenticationOptions<MsalProviderOptions>>(
            options =>
            {
                scopes?.ForEach((scope) =>
                {
                    options.ProviderOptions.DefaultAccessTokenScopes.Add(scope);
                });
            });

        services.AddScoped<IAuthenticationProvider, GraphAuthenticationProvider>();

        services.AddScoped<IHttpProvider, HttpClientHttpProvider>(sp =>
            new HttpClientHttpProvider(new HttpClient()));

        services.AddScoped(sp =>
        {
            return new GraphServiceClient(
                baseUrl,
                sp.GetRequiredService<IAuthenticationProvider>(),
                sp.GetRequiredService<IHttpProvider>());
        });

        return services;
    }

    private class GraphAuthenticationProvider(IAccessTokenProvider tokenProvider, 
        IConfiguration config) : IAuthenticationProvider
    {
        private readonly IConfiguration config = config;

        public IAccessTokenProvider TokenProvider { get; } = tokenProvider;

        public async Task AuthenticateRequestAsync(HttpRequestMessage request)
        {
            var result = await TokenProvider.RequestAccessToken(
                new AccessTokenRequestOptions()
                { 
                    Scopes = config.GetSection("MicrosoftGraph:Scopes").Get<string[]>()
                });

            if (result.TryGetToken(out var token))
            {
                request.Headers.Authorization ??= new AuthenticationHeaderValue(
                    "Bearer", token.Value);
            }
        }
    }

    private class HttpClientHttpProvider(HttpClient client) : IHttpProvider
    {
        private readonly HttpClient client = client;

        public ISerializer Serializer { get; } = new Serializer();

        public TimeSpan OverallTimeout { get; set; } = TimeSpan.FromSeconds(300);

        public Task<HttpResponseMessage> SendAsync(HttpRequestMessage request)
        {
            return client.SendAsync(request);
        }

        public Task<HttpResponseMessage> SendAsync(HttpRequestMessage request,
            HttpCompletionOption completionOption,
            CancellationToken cancellationToken)
        {
            return client.SendAsync(request, completionOption, cancellationToken);
        }

        public void Dispose()
        {
        }
    }
}

Внимание

AdditionalScopesToConsentDefaultAccessTokenScopes Дополнительные сведения о том, почему предыдущий код использует DefaultAccessTokenScopes для добавления область вместо AdditionalScopesToConsentраздела .

В файле добавьте клиентские Program службы Graph и конфигурацию с AddGraphClient помощью метода расширения:

var baseUrl = builder.Configuration
    .GetSection("MicrosoftGraph")["BaseUrl"];
var scopes = builder.Configuration.GetSection("MicrosoftGraph:Scopes")
    .Get<List<string>>();

builder.Services.AddGraphClient(baseUrl, scopes);

Вызов API Graph из компонента с помощью пакета SDK для Graph

UserData Следующий компонент использует внедренный GraphServiceClient объект для получения данных профиля ME-ID пользователя и отображения номера мобильного телефона. Для любого тестового пользователя, который вы создаете в ME-ID, убедитесь, что вы предоставите профилю ME-ID пользователя номер мобильного телефона в портал Azure.

UserData.razor:

@page "/user-data"
@using Microsoft.AspNetCore.Authorization
@using Microsoft.Graph
@attribute [Authorize]
@inject GraphServiceClient Client

<PageTitle>User Data</PageTitle>

<h1>Microsoft Graph User Data</h1>

@if (!string.IsNullOrEmpty(user?.MobilePhone))
{
    <p>Mobile Phone: @user.MobilePhone</p>
}

@code {
    private Microsoft.Graph.User? user;

    protected override async Task OnInitializedAsync()
    {
        var request = Client.Me.Request();
        user = await request.GetAsync();
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-data">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Data
    </NavLink>
</div>

Совет

Сведения о добавлении пользователей в приложение см. в разделе "Назначение пользователей регистрации приложения" с ролями приложений или без нее.

При локальном тестировании с помощью пакета SDK Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieпомехи тестам. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Настройка утверждений пользователей с помощью пакета SDK Graph

В следующем примере приложение создает мобильный номер телефона и утверждения о расположении офиса для пользователя из данных профиля пользователя ME-ID. Приложение должно иметь API Graph, область настроенный User.Read в ME-ID. Все тестовые пользователи для этого сценария должны иметь номер мобильного телефона и офис в своем профиле ME-ID, который можно добавить через портал Azure.

В следующей фабрике пользовательских учетных записей пользователей:

  • Значение (ILoggerlogger) включается для удобства, если вы хотите регистрировать сведения или ошибки в методеCreateUserAsync.
  • AccessTokenNotAvailableException При возникновении ошибки пользователь перенаправляется в поставщик удостоверений для входа в учетную запись. При запросе маркера доступа могут выполняться дополнительные или различные действия. Например, приложение может записать AccessTokenNotAvailableException и создать запрос в службу поддержки для дальнейшего изучения.
  • RemoteUserAccount Платформа представляет учетную запись пользователя. Если приложению требуется пользовательский класс учетной записи пользователя, который расширяется RemoteUserAccount, переключите класс пользовательской учетной записи пользователя на RemoteUserAccount следующий код.

CustomAccountFactory.cs:

using System.Security.Claims;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication.Internal;
using Microsoft.Graph;

namespace BlazorSample;

public class CustomAccountFactory(IAccessTokenProviderAccessor accessor, 
        IServiceProvider serviceProvider, ILogger<CustomAccountFactory> logger)
    : AccountClaimsPrincipalFactory<RemoteUserAccount>(accessor)
{
    private readonly ILogger<CustomAccountFactory> logger = logger;
    private readonly IServiceProvider serviceProvider = serviceProvider;

    public override async ValueTask<ClaimsPrincipal> CreateUserAsync(
        RemoteUserAccount account,
        RemoteAuthenticationUserOptions options)
    {
        var initialUser = await base.CreateUserAsync(account, options);

        if (initialUser.Identity is not null && 
            initialUser.Identity.IsAuthenticated)
        {
            var userIdentity = initialUser.Identity as ClaimsIdentity;

            if (userIdentity is not null)
            {
                try
                {
                    var client = ActivatorUtilities
                        .CreateInstance<GraphServiceClient>(serviceProvider);
                    var request = client.Me.Request();
                    var user = await request.GetAsync();

                    if (user is not null)
                    {
                        userIdentity.AddClaim(new Claim("mobilephone",
                            user.MobilePhone ?? "(000) 000-0000"));
                        userIdentity.AddClaim(new Claim("officelocation",
                            user.OfficeLocation ?? "Not set"));
                    }
                }
                catch (AccessTokenNotAvailableException exception)
                {
                    exception.Redirect();
                }
            }
        }

        return initialUser;
    }
}

Настройте проверку подлинности MSAL для использования фабрики пользовательских учетных записей пользователей.

Убедитесь, что Program файл использует Microsoft.AspNetCore.Components.WebAssembly.Authentication пространство имен:

using Microsoft.AspNetCore.Components.WebAssembly.Authentication;

Пример в этом разделе основан на подходе чтения базового URL-адреса с версией и область из конфигурации приложения с помощью MicrosoftGraph раздела в wwwroot/appsettings.json файле. Следующие строки уже должны присутствовать в Program файле, следуя инструкциям, приведенным ранее в этой статье:

var baseUrl = string.Join("/", 
    builder.Configuration.GetSection("MicrosoftGraph")["BaseUrl"];
var scopes = builder.Configuration.GetSection("MicrosoftGraph:Scopes")
    .Get<List<string>>();

builder.Services.AddGraphClient(baseUrl, scopes);

Program В файле найдите вызов AddMsalAuthentication метода расширения. Обновите код до следующего, включив вызов, который AddAccountClaimsPrincipalFactory добавляет фабрику субъектов утверждений учетной записи с помощью CustomAccountFactory.

Если приложение использует пользовательский класс учетной записи пользователя, RemoteUserAccountрасширяющийся, переключите класс пользовательской учетной записи пользователя на RemoteUserAccount следующий код.

builder.Services.AddMsalAuthentication<RemoteAuthenticationState,
    RemoteUserAccount>(options =>
    {
        builder.Configuration.Bind("AzureAd", 
            options.ProviderOptions.Authentication);
    })
    .AddAccountClaimsPrincipalFactory<RemoteAuthenticationState, RemoteUserAccount,
        CustomAccountFactory>();

Чтобы изучить утверждения пользователя после проверки подлинности пользователя с помощью ME-ID, можно использовать следующий UserClaims компонент:

UserClaims.razor:

@page "/user-claims"
@using System.Security.Claims
@using Microsoft.AspNetCore.Authorization
@attribute [Authorize]
@inject AuthenticationStateProvider AuthenticationStateProvider

<h1>User Claims</h1>

@if (claims.Any())
{
    <ul>
        @foreach (var claim in claims)
        {
            <li>@claim.Type: @claim.Value</li>
        }
    </ul>
}
else
{
    <p>No claims found.</p>
}

@code {
    private IEnumerable<Claim> claims = Enumerable.Empty<Claim>();

    protected override async Task OnInitializedAsync()
    {
        var authState = await AuthenticationStateProvider
            .GetAuthenticationStateAsync();
        var user = authState.User;

        claims = user.Claims;
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-claims">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Claims
    </NavLink>
</div>

При локальном тестировании с помощью пакета SDK Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieпомехи тестам. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

В следующих примерах используется именованный HttpClient для вызовов API Graph для получения мобильного номера телефона пользователя для обработки звонка или настройки утверждений пользователя для включения утверждения номера мобильного телефона и утверждения расположения офиса.

В примерах требуется ссылка на пакет для Microsoft.Extensions.Http автономного Blazor WebAssembly приложения.

В примерах требуется ссылка на пакет для Microsoft.Extensions.Http автономного Blazor WebAssembly приложения или Client приложения размещенного Blazor WebAssembly решения.

Примечание.

Рекомендации по добавлению пакетов в приложения .NET см. в разделе Способы установки пакетов NuGet в статье Рабочий процесс использования пакета (документация по NuGet). Проверьте правильность версий пакета на сайте NuGet.org.

В портал Azure предоставьте делегированные разрешения (область)† для данных Microsoft Graph, к которым приложение должно иметь доступ от имени пользователя. Например, в этой статье регистрация приложения должна включать делегированное разрешение на чтение данных пользователя (Microsoft.Graph>User.Readобласть в разрешениях API, Тип: Делегировано). Область User.Read позволяет пользователям входить в приложение и позволяет приложению читать сведения о профиле и компании пользователей, вошедшего в систему. Дополнительные сведения см. в разделе "Обзор разрешений и согласия" в платформа удостоверений Майкрософт и обзоре разрешений Microsoft Graph.

Примечание.

†Permissions и область означает то же самое и используется взаимозаменяемо в документации по безопасности и портал Azure. В этой статье используются область/ область при обращении к разрешениям API Graph.

После добавления api Microsoft Graph область в регистрацию приложения в портал Azure добавьте в файл в приложении следующую конфигурацию wwwroot/appsettings.json параметров приложения, которая включает базовый URL-адрес Graph с версией Microsoft Graph и область. В следующем примере User.Read область указывается для примеров в последующих разделах этой статьи. Области не учитывает регистр.

"MicrosoftGraph": {
  "BaseUrl": "https://graph.microsoft.com/{VERSION}/",
  "Scopes": [
    "user.read"
  ]
}

В предыдущем примере заполнитель — это версия API Microsoft Graph (например: {VERSION}v1.0). Косая черта требуется.

Ниже приведен пример полного wwwroot/appsettings.json файла конфигурации для приложения, использующего ME-ID в качестве поставщика удостоверений, где для Microsoft Graph указывается чтение пользовательских данных (user.readобласть).

{
  "AzureAd": {
    "Authority": "https://login.microsoftonline.com/{TENANT ID}",
    "ClientId": "{CLIENT ID}",
    "ValidateAuthority": true
  },
  "MicrosoftGraph": {
    "BaseUrl": "https://graph.microsoft.com/v1.0/",
    "Scopes": [
      "user.read"
    ]
  }
}

В предыдущем примере {TENANT ID} заполнитель — это идентификатор каталога (клиента), а {CLIENT ID} заполнитель — идентификатор приложения (клиента). Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Создайте следующий GraphAuthorizationMessageHandler класс и конфигурацию проекта в Program файле для работы с API Graph. Базовый URL-адрес и область предоставляются обработчику из конфигурации.

GraphAuthorizationMessageHandler.cs:

using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication;

namespace BlazorSample;

public class GraphAuthorizationMessageHandler : AuthorizationMessageHandler
{
    public GraphAuthorizationMessageHandler(IAccessTokenProvider provider,
        NavigationManager navigation, IConfiguration config)
        : base(provider, navigation)
    {
        ConfigureHandler(
            authorizedUrls: [ config.GetSection("MicrosoftGraph")["BaseUrl"] ?? 
                string.Empty ],
            scopes: config.GetSection("MicrosoftGraph:Scopes").Get<List<string>>());
    }
}

Program В файле настройте именованный HttpClient API Graph:

builder.Services.AddTransient<GraphAuthorizationMessageHandler>();

builder.Services.AddHttpClient("GraphAPI",
        client => client.BaseAddress = new Uri(
            builder.Configuration.GetSection("MicrosoftGraph")["BaseUrl"] ?? 
                string.Empty))
    .AddHttpMessageHandler<GraphAuthorizationMessageHandler>();

В предыдущем примере класс DelegatingHandlerGraphAuthorizationMessageHandler регистрируется как временная служба для AddHttpMessageHandler. Временную регистрацию рекомендуется использовать для интерфейса IHttpClientFactory, который управляет собственными областями внедрения зависимостей. Дополнительные сведения см. на следующих ресурсах:

Вызов API Graph из компонента с помощью именованного HttpClient

Класс UserInfo.cs назначает требуемые свойства профиля пользователя атрибутом JsonPropertyNameAttribute и JSименем ON, используемым ME-ID. В следующем примере настраивается свойства для номера мобильного телефона пользователя и расположения офиса.

UserInfo.cs:

using System.Text.Json.Serialization;

namespace BlazorSample;

public class UserInfo
{
    [JsonPropertyName("mobilePhone")]
    public string? MobilePhone { get; set; }

    [JsonPropertyName("officeLocation")]
    public string? OfficeLocation { get; set; }
}

В следующем UserData компоненте HttpClient создается API Graph для выдачи запроса на данные профиля пользователя. Ресурс me (me) добавляется в базовый URL-адрес с версией запроса API Graph. JSДанные ON, возвращаемые Graph, десериализируются в UserInfo свойства класса. В следующем примере получается номер мобильного телефона. Вы можете добавить аналогичный код, чтобы включить расположение офиса профиля ME-ID пользователя, если вы хотите (userInfo.OfficeLocation). Если запрос маркера доступа завершается сбоем, пользователь перенаправляется для входа в приложение для нового маркера доступа.

UserData.razor:

@page "/user-data"
@using Microsoft.AspNetCore.Authorization
@using Microsoft.AspNetCore.Components.WebAssembly.Authentication
@attribute [Authorize]
@inject IConfiguration Config
@inject IHttpClientFactory ClientFactory

<PageTitle>User Data</PageTitle>

<h1>Microsoft Graph User Data</h1>

@if (!string.IsNullOrEmpty(userInfo?.MobilePhone))
{
    <p>Mobile Phone: @userInfo.MobilePhone</p>
}

@code {
    private UserInfo? userInfo;

    protected override async Task OnInitializedAsync()
    {
        try
        {
            var client = ClientFactory.CreateClient("GraphAPI");

            userInfo = await client.GetFromJsonAsync<UserInfo>("me");
        }
        catch (AccessTokenNotAvailableException exception)
        {
            exception.Redirect();
        }
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-data">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Data
    </NavLink>
</div>

Совет

Сведения о добавлении пользователей в приложение см. в разделе "Назначение пользователей регистрации приложения" с ролями приложений или без нее.

В следующей последовательности описывается новый поток пользователя для область API Graph:

  1. Новый пользователь впервые входит в приложение.
  2. Пользователь дает согласие на использование приложения в пользовательском интерфейсе согласия Azure.
  3. Пользователь обращается к странице компонента, которая запрашивает данные API Graph в первый раз.
  4. Пользователь перенаправляется в пользовательский интерфейс согласия Azure для предоставления согласия на область API Graph.
  5. Возвращается данные пользователя API Graph.

Если вы предпочитаете, что область подготовка (согласие для область API Graph) выполняется при первоначальном входе, укажите область проверку подлинности MSAL в качестве область маркера доступа по умолчанию в Program файле:

+ var scopes = builder.Configuration.GetSection("MicrosoftGraph:Scopes")
+     .Get<List<string>>() ?? [];

builder.Services.AddMsalAuthentication(options =>
{
    builder.Configuration.Bind("AzureAd", options.ProviderOptions.Authentication);

+   foreach (var scope in scopes)
+   {
+       options.ProviderOptions.DefaultAccessTokenScopes.Add(scope);
+   }
});

Внимание

AdditionalScopesToConsentDefaultAccessTokenScopes Дополнительные сведения о том, почему предыдущий код использует DefaultAccessTokenScopes для добавления область вместо AdditionalScopesToConsentраздела .

При внесении предыдущих изменений в приложение поток пользователя принимает следующую последовательность:

  1. Новый пользователь впервые входит в приложение.
  2. Пользователь дает согласие на использование приложений и API Graph область в пользовательском интерфейсе согласия Azure.
  3. Пользователь обращается к странице компонента, которая запрашивает данные API Graph в первый раз.
  4. Возвращается данные пользователя API Graph.

При локальном тестировании с помощью API Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieвмешательство в тестирование. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Настройка утверждений пользователей с помощью именованного HttpClient

В следующем примере приложение создает мобильный номер телефона и утверждения о расположении офиса для пользователя из данных профиля пользователя ME-ID. Приложение должно иметь API Graph, область настроенный User.Read в ME-ID. Тестовые учетные записи пользователей в ME-ID требуют записи для номера мобильного телефона и расположения офиса, которые можно добавить с помощью портал Azure в профили пользователей.

Если вы еще не добавили UserInfo класс в приложение, следуя инструкциям, приведенным ранее в этой статье, добавьте следующий класс и назначьте требуемые свойства профиля пользователя атрибутом JsonPropertyNameAttribute и JSименем ON, используемому ME-ID. В следующем примере настраивается свойства для номера мобильного телефона пользователя и расположения офиса.

UserInfo.cs:

using System.Text.Json.Serialization;

namespace BlazorSample;

public class UserInfo
{
    [JsonPropertyName("mobilePhone")]
    public string? MobilePhone { get; set; }

    [JsonPropertyName("officeLocation")]
    public string? OfficeLocation { get; set; }
}

В следующей фабрике пользовательских учетных записей пользователей:

  • Значение (ILoggerlogger) включается для удобства, если вы хотите регистрировать сведения или ошибки в методеCreateUserAsync.
  • AccessTokenNotAvailableException При возникновении ошибки пользователь перенаправляется в поставщик удостоверений для входа в учетную запись. При запросе маркера доступа могут выполняться дополнительные или различные действия. Например, приложение может записать AccessTokenNotAvailableException и создать запрос в службу поддержки для дальнейшего изучения.
  • RemoteUserAccount Платформа представляет учетную запись пользователя. Если приложению требуется настраиваемый класс учетной записи пользователя, расширяющий RemoteUserAccount, замените RemoteUserAccount на этот класс в следующем коде.

CustomAccountFactory.cs:

using System.Net.Http.Json;
using System.Security.Claims;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication;
using Microsoft.AspNetCore.Components.WebAssembly.Authentication.Internal;

namespace BlazorSample;

public class CustomAccountFactory(IAccessTokenProviderAccessor accessor,
        IHttpClientFactory clientFactory,
        ILogger<CustomAccountFactory> logger)
    : AccountClaimsPrincipalFactory<RemoteUserAccount>(accessor)
{
    private readonly ILogger<CustomAccountFactory> logger = logger;
    private readonly IHttpClientFactory clientFactory = clientFactory;

    public override async ValueTask<ClaimsPrincipal> CreateUserAsync(
        RemoteUserAccount account,
        RemoteAuthenticationUserOptions options)
    {
        var initialUser = await base.CreateUserAsync(account, options);

        if (initialUser.Identity is not null && 
            initialUser.Identity.IsAuthenticated)
        {
            var userIdentity = initialUser.Identity as ClaimsIdentity;

            if (userIdentity is not null)
            {
                try
                {
                    var client = clientFactory.CreateClient("GraphAPI");

                    var userInfo = await client.GetFromJsonAsync<UserInfo>("me");

                    if (userInfo is not null)
                    {
                        userIdentity.AddClaim(new Claim("mobilephone",
                            userInfo.MobilePhone ?? "(000) 000-0000"));
                        userIdentity.AddClaim(new Claim("officelocation",
                            userInfo.OfficeLocation ?? "Not set"));
                    }
                }
                catch (AccessTokenNotAvailableException exception)
                {
                    exception.Redirect();
                }
            }
        }

        return initialUser;
    }
}

Проверка подлинности MSAL настроена для использования фабрики пользовательских учетных записей пользователей. Сначала убедитесь, что Program файл использует Microsoft.AspNetCore.Components.WebAssembly.Authentication пространство имен:

using Microsoft.AspNetCore.Components.WebAssembly.Authentication;

Program В файле найдите вызов AddMsalAuthentication метода расширения. Обновите код до следующего, включив вызов, который AddAccountClaimsPrincipalFactory добавляет фабрику субъектов утверждений учетной записи с помощью CustomAccountFactory.

Если приложение использует пользовательский класс учетной записи пользователя, который расширяется RemoteUserAccount, переключите класс пользовательской учетной записи пользователя приложения на RemoteUserAccount следующий код.

builder.Services.AddMsalAuthentication<RemoteAuthenticationState, 
    RemoteUserAccount>(options =>
    {
        builder.Configuration.Bind("AzureAd", 
            options.ProviderOptions.Authentication);
    })
    .AddAccountClaimsPrincipalFactory<RemoteAuthenticationState, RemoteUserAccount, 
        CustomAccountFactory>();

Предыдущий пример предназначен для приложения, использующего проверку подлинности ME-ID с MSAL. Аналогичные шаблоны имеются для проверки подлинности OIDC и API. Дополнительные сведения см. в примерах в разделе "Настройка пользователя с использованием полезных данных" статьи о дополнительных сценариях безопасности ASP.NET Core Blazor WebAssembly.

Чтобы изучить утверждения пользователя после проверки подлинности пользователя с помощью ME-ID, можно использовать следующий UserClaims компонент:

UserClaims.razor:

@page "/user-claims"
@using System.Security.Claims
@using Microsoft.AspNetCore.Authorization
@attribute [Authorize]
@inject AuthenticationStateProvider AuthenticationStateProvider

<h1>User Claims</h1>

@if (claims.Any())
{
    <ul>
        @foreach (var claim in claims)
        {
            <li>@claim.Type: @claim.Value</li>
        }
    </ul>
}
else
{
    <p>No claims found.</p>
}

@code {
    private IEnumerable<Claim> claims = Enumerable.Empty<Claim>();

    protected override async Task OnInitializedAsync()
    {
        var authState = await AuthenticationStateProvider
            .GetAuthenticationStateAsync();
        var user = authState.User;

        claims = user.Claims;
    }
}

Добавьте ссылку на страницу компонента в NavMenu компоненте (Layout/NavMenu.razor):

<div class="nav-item px-3">
    <NavLink class="nav-link" href="user-claims">
        <span class="bi bi-list-nested-nav-menu" aria-hidden="true"></span> User Claims
    </NavLink>
</div>

При локальном тестировании с помощью API Graph рекомендуется использовать новый сеанс браузера InPrivate/incognito для каждого теста, чтобы предотвратить cookieвмешательство в тестирование. Дополнительные сведения см. в статье "Защита автономного приложения ASP.NET Core Blazor WebAssembly с помощью идентификатора Microsoft Entra.

Назначение пользователям регистрации приложения с ролями приложения или без нее

Вы можете добавить пользователей в регистрацию приложения и назначить роли пользователям, выполнив следующие действия в портал Azure.

Чтобы добавить пользователя, выберите "Пользователи" в области "ME-ID" портал Azure:

  1. Выберите "Создать пользователя>".
  2. Используйте шаблон создания пользователя.
  3. Укажите сведения о пользователе в Identity этой области.
  4. Вы можете создать исходный пароль или назначить начальный пароль, который пользователь изменяет при первом входе. Если вы используете пароль, созданный порталом, запишите его сейчас.
  5. Нажмите кнопку "Создать" , чтобы создать пользователя. При закрытии нового пользовательского интерфейса выберите "Обновить ", чтобы обновить список пользователей и показать нового пользователя.
  6. В примерах этой статьи назначьте номер мобильного телефона новому пользователю, выбрав свое имя из списка пользователей, выбрав свойства и изменив контактные данные для предоставления номера мобильного телефона.

Чтобы назначить пользователей приложению без ролей приложения:

  1. В области me-ID портал Azure откройте корпоративные приложения.
  2. Выберите приложение из списка.
  3. Выберите Пользователи и группы
  4. Выберите Добавить пользователя или группу.
  5. Выберите пользователя.
  6. Нажмите кнопку Назначить.

Чтобы назначить пользователей приложению ролями приложения, выполните следующие действия.

  1. Добавьте роли в регистрацию приложения в портал Azure после указания в ASP.NET Core Blazor WebAssembly с группами и ролями идентификаторов Microsoft Entra.
  2. В области me-ID портал Azure откройте корпоративные приложения.
  3. Выберите приложение из списка.
  4. Выберите Пользователи и группы
  5. Выберите Добавить пользователя или группу.
  6. Выберите пользователя и выберите свою роль для доступа к приложению. Несколько ролей назначаются пользователю, повторяя процесс добавления пользователя в приложение до тех пор, пока не будут назначены все роли для пользователя. Пользователи с несколькими ролями указываются один раз для каждой назначенной роли в списке пользователей и групп для приложения.
  7. Нажмите кнопку Назначить.

DefaultAccessTokenScopes и AdditionalScopesToConsent

Примеры, приведенные в этой статье, подготавливают API Graph область с DefaultAccessTokenScopes, а не AdditionalScopesToConsent.

AdditionalScopesToConsentне используется, так как не удается подготовить область API Graph для пользователей при первом входе в приложение с помощью MSAL через пользовательский интерфейс согласия Azure. Когда пользователь пытается получить доступ к API Graph впервые с помощью пакета SDK Graph, он сталкивается с исключением:

Microsoft.Graph.Models.ODataErrors.ODataError: Access token is empty.

После того как пользователь подготавливает api Graph область, предоставленных черезDefaultAccessTokenScopes, приложение может использовать AdditionalScopesToConsent для последующего входа пользователя. Однако изменение кода приложения не имеет смысла для рабочего приложения, которое требует периодического добавления новых пользователей с делегированными область Graph или добавление новых делегированных API Graph область в приложение.

Предыдущее обсуждение подготовки область для доступа к API Graph при первом входе пользователя в приложение применяется только к:

  • Приложения, использующие пакет SDK Graph.
  • Приложения, использующие доступ к API Graph с именемHttpClient, которые запрашивают у пользователей согласие на область Graph при первом входе в приложение.

При использовании именованногоHttpClient, который не запрашивает у пользователей согласие на область Graph при первом входе, пользователи перенаправляются в пользовательский интерфейс согласия Azure для API Graph, область согласие при первом запросе доступа к API Graph через DelegatingHandler предварительно настроенное имяHttpClient. Если область Graph изначально не согласуются с именованным HttpClient подходом, ни DefaultAccessTokenScopesAdditionalScopesToConsent вызываются приложением. Дополнительные сведения см. в описании именованного HttpClient покрытия в этой статье.

Размещенные Blazor WebAssembly решения

Примеры, описанные в этой статье, относятся к использованию пакета SDK Graph или именованного HttpClient API Graph непосредственно из автономного Blazor WebAssembly приложения или непосредственно из Client приложения размещенного Blazor WebAssemblyрешения. Дополнительный сценарий, который не рассматривается в этой статье, предназначен для приложения размещенного решения для вызова Server приложения решения через веб-API, а затем Server приложение использует пакет SDK или API Graph для Client вызова Microsoft Graph и возврата данных в Client приложение. Хотя это поддерживаемый подход, он не рассматривается в этой статье. Если вы хотите применить этот подход:

  • Следуйте инструкциям в руководстве по вызову веб-API из приложения ASP.NET Core Blazor для аспектов веб-API по выдаче запросов Server приложению из Client приложения и возврате данных Client в приложение.
  • Следуйте указаниям в основной документации по Microsoft Graph, чтобы использовать пакет SDK Graph с типичным приложением ASP.NET Core, которое в этом сценарии является Server приложением решения. Если вы используете Blazor WebAssembly шаблон проекта для создания размещенного Blazor WebAssembly решения (ASP.NET Core Hosted-h|--hosted/) с авторизацией организации (одной организацией илиSingleOrg несколькими организациями/MultiOrg) и параметром Microsoft Graph (платформа удостоверений Майкрософт> Подключение добавленные службы>Microsoft Graph разрешения в Visual Studio или --calls-graph параметр с помощью команды .NET CLIdotnet new), Server приложение решения настраивается для использования пакета SDK Graph при создании решения из шаблона проекта.

Дополнительные ресурсы

Общее руководство

Руководство по безопасности