Freigeben über


ASP.NET Core Blazor-Authentifizierungsstatus

Hinweis

Dies ist nicht die neueste Version dieses Artikels. Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.

Warnung

Diese Version von ASP.NET Core wird nicht mehr unterstützt. Weitere Informationen finden Sie in der Supportrichtlinie für .NET und .NET Core. Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.

Wichtig

Diese Informationen beziehen sich auf ein Vorabversionsprodukt, das vor der kommerziellen Freigabe möglicherweise noch wesentlichen Änderungen unterliegt. Microsoft gibt keine Garantie, weder ausdrücklich noch impliziert, hinsichtlich der hier bereitgestellten Informationen.

Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.

In diesem Artikel wird erklärt, wie Sie einen benutzerdefinierten Authentifizierungsstatusanbieter erstellen und Benachrichtigungen über Änderungen des Authentifizierungsstatus von Benutzenden im Code erhalten.

Die allgemeinen Ansätze für serverseitige und clientseitige Blazor-Apps sind ähnlich, unterscheiden sich jedoch in der genauen Umsetzung. Daher befasst sich dieser Artikel sowohl mit serverseitigen Blazor- als auch mit clientseitigen Blazor-Apps. Verwenden Sie den Pivot-Selektor oben im Artikel, um den Pivot des Artikels an die Art des Blazor-Projekts anzupassen, mit dem Sie arbeiten:

  • Serveseitige Blazor-Apps (Server-Pivot): Blazor Server für .NET 7 oder niedriger und das Serverprojekt von Blazor Web App für .NET 8 oder höher.
  • Clientseitige Blazor-Apps (Blazor WebAssembly-Pivot): Blazor WebAssembly für alle Versionen von .NET oder das .Client-Projekt eines Blazor Web App für .NET 8 oder höher.

Abstrakte AuthenticationStateProvider-Klasse

Das Blazor-Framework enthält eine abstrakte AuthenticationStateProvider-Klasse, um Informationen zum Authentifizierungsstatus von aktuellen Benutzenden mit den folgenden Mitgliedern bereitzustellen:

  • GetAuthenticationStateAsync: Ruft asynchron den Authentifizierungsstatus des aktuellen Benutzenden ab.
  • AuthenticationStateChanged: Ein Ereignis, das Benachrichtigungen bereitstellt, wenn sich der Authentifizierungsstatus geändert hat. Dieses Ereignis kann beispielsweise ausgelöst werden, wenn sich ein Benutzender bei der App anmeldet oder abmeldet.
  • NotifyAuthenticationStateChanged: Löst ein Ereignis aus, bei dem sich der Authentifizierungsstatus geändert hat.

Implementieren einer benutzerdefinierten Instanz von AuthenticationStateProvider

Die App muss auf das Microsoft.AspNetCore.Components.Authorization-NuGet-Paket verweisen, das Authentifizierungs- und Autorisierungsunterstützung für Blazor-Apps bietet.

Hinweis

Einen Leitfaden zum Hinzufügen von Paketen zu .NET-Apps finden Sie in Installieren und Verwalten von Paketen unter Workflow der Nutzung von Paketen (NuGet-Dokumentation). Überprüfen Sie unter NuGet.org, ob die richtige Paketversion verwendet wird.

Konfigurieren Sie die folgenden Authentifizierungs-, Autorisierungs- und kaskadierenden Authentifizierungsstatusdienste in der Program-Datei.

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, ist die App mit den folgenden Dienstregistrierungen vorkonfiguriert, was die Offenlegung des Authentifizierungsstatus als kaskadierenden Parameter einschließt. Weitere Informationen finden Sie unter ASP.NET Core Blazor-Authentifizierung und -Autorisierung mit zusätzlichen Informationen im Abschnitt Anpassen nicht autorisierter Inhalte mit der Router-Komponente des Artikels.

using Microsoft.AspNetCore.Components.Authorization;

...

builder.Services.AddAuthorization();
builder.Services.AddCascadingAuthenticationState();

Konfigurieren Sie die Authentifizierungs- und Autorisierungsdienste in der Program-Datei.

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, enthält die App die folgende Dienstregistrierung.

using Microsoft.AspNetCore.Components.Authorization;

...

builder.Services.AddAuthorization();

Konfigurieren Sie Authentifizierungs- und Autorisierungsdienste in Startup.ConfigureServices von Startup.cs.

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, enthält die App die folgende Dienstregistrierung.

using Microsoft.AspNetCore.Components.Authorization;

...

services.AddAuthorization();

Konfigurieren Sie in Blazor WebAssembly-Apps (alle .NET-Versionen) oder im .Client-Projekt eines Blazor Web App (.NET 8 oder höher) die Authentifizierung, Autorisierung und kaskadierenden Authentifizierungsstatusdienste in der Program-Datei.

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, ist die App mit den folgenden Dienstregistrierungen vorkonfiguriert, was die Offenlegung des Authentifizierungsstatus als kaskadierenden Parameter einschließt. Weitere Informationen finden Sie unter ASP.NET Core Blazor-Authentifizierung und -Autorisierung mit zusätzlichen Informationen im Abschnitt Anpassen nicht autorisierter Inhalte mit der Router-Komponente des Artikels.

using Microsoft.AspNetCore.Components.Authorization;

...

builder.Services.AddAuthorizationCore();
builder.Services.AddCascadingAuthenticationState();

Konfigurieren Sie die Authentifizierungs- und Autorisierungsdienste in der Program-Datei.

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, enthält die App die folgende Dienstregistrierung.

using Microsoft.AspNetCore.Components.Authorization;

...

builder.Services.AddAuthorizationCore();

Erstellen Sie eine Unterklasse AuthenticationStateProvider und überschreiben Sie GetAuthenticationStateAsync, um den Authentifizierungsstatus der Benutzenden zu erstellen. Im folgenden Beispiel werden alle Benutzer mit dem Benutzernamen mrfibuli authentifiziert.

CustomAuthStateProvider.cs:

using System.Security.Claims;
using Microsoft.AspNetCore.Components.Authorization;

public class CustomAuthStateProvider : AuthenticationStateProvider
{
    public override Task<AuthenticationState> GetAuthenticationStateAsync()
    {
        var identity = new ClaimsIdentity(
        [
            new Claim(ClaimTypes.Name, "mrfibuli"),
        ], "Custom Authentication");

        var user = new ClaimsPrincipal(identity);

        return Task.FromResult(new AuthenticationState(user));
    }
}

Hinweis

Der vorangehende Code, der eine neue ClaimsIdentity erstellt, verwendet die mit C# 12 (.NET 8) eingeführte vereinfachte Initialisierung der Auflistung. Weitere Informationen finden Sie unter Sammlungsausdrücke – C#-Sprachreferenz.

Der CustomAuthStateProvider-Dienst wird in der Program-Datei registriert. Registrieren Sie den Dienst scoped mit AddScoped:

builder.Services.AddScoped<AuthenticationStateProvider, CustomAuthStateProvider>();

In einer Blazor Server-App registrieren Sie den Dienst scoped mit AddScopednach dem Aufruf von AddServerSideBlazor:

builder.Services.AddServerSideBlazor();

builder.Services.AddScoped<AuthenticationStateProvider, CustomAuthStateProvider>();

In einer Blazor Server-App registrieren Sie den Dienst scoped mit AddScopednach dem Aufruf von AddServerSideBlazor:

services.AddServerSideBlazor();

services.AddScoped<AuthenticationStateProvider, CustomAuthStateProvider>();

Der CustomAuthStateProvider-Dienst wird in der Program-Datei registriert. Registrieren Sie den Dienst Singleton mit AddSingleton:

builder.Services.AddSingleton<AuthenticationStateProvider, CustomAuthStateProvider>();

Wenn er nicht vorhanden ist, fügen Sie der _Imports.razor-Datei eine @using-Anweisung hinzu, um den Microsoft.AspNetCore.Components.Authorization-Namespace komponentenübergreifend verfügbar zu machen:

@using Microsoft.AspNetCore.Components.Authorization;

Bestätigen oder ändern Sie die Routenansichtskomponente in eine AuthorizeRouteView in der Router-Komponentendefinition. Der Speicherort der Router-Komponente unterscheidet sich je nach App-Typ. Verwenden Sie die Suche, um die Komponente zu finden, wenn Sie den Speicherort im Projekt nicht kennen.

<Router ...>
    <Found ...>
        <AuthorizeRouteView RouteData="routeData" 
            DefaultLayout="typeof(Layout.MainLayout)" />
        ...
    </Found>
</Router>

Hinweis

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, beinhaltet die App die AuthorizeRouteView-Komponente. Weitere Informationen finden Sie unter ASP.NET Core Blazor-Authentifizierung und -Autorisierung mit zusätzlichen Informationen im Abschnitt Anpassen nicht autorisierter Inhalte mit der Router-Komponente des Artikels.

Im Speicherort der Router-Komponente:

Der Speicherort der Router-Komponente unterscheidet sich je nach App-Typ. Verwenden Sie die Suche, um die Komponente zu finden, wenn Sie den Speicherort im Projekt nicht kennen.

<CascadingAuthenticationState>
    <Router ...>
        <Found ...>
            <AuthorizeRouteView RouteData="routeData" 
                DefaultLayout="typeof(MainLayout)" />
            ...
        </Found>
    </Router>
</CascadingAuthenticationState>

Hinweis

Wenn Sie eine Blazor-App aus einer der Blazor-Projektvorlagen mit aktivierter Authentifizierung erstellen, enthält die App AuthorizeRouteView- und CascadingAuthenticationState-Komponenten. Weitere Informationen finden Sie unter ASP.NET Core Blazor-Authentifizierung und -Autorisierung mit zusätzlichen Informationen im Abschnitt Anpassen nicht autorisierter Inhalte mit der Router-Komponente des Artikels.

Die folgende Beispielkomponente AuthorizeView veranschaulicht den Namen des authentifizierten Benutzenden:

<AuthorizeView>
    <Authorized>
        <p>Hello, @context.User.Identity?.Name!</p>
    </Authorized>
    <NotAuthorized>
        <p>You're not authorized.</p>
    </NotAuthorized>
</AuthorizeView>

Anleitungen zur Verwendung von AuthorizeView finden Sie unter ASP.NET Core Blazor-Authentifizierung und -Autorisierung.

Änderungsbenachrichtigungen für den Authentifizierungsstatus

Ein benutzerdefinierter AuthenticationStateProvider kann NotifyAuthenticationStateChanged für die AuthenticationStateProvider-Basisklasse aufrufen, um Consumer über die Änderung des Authentifizierungsstatus zu benachrichtigen.

Das folgende Beispiel basiert auf der Implementierung eines benutzerdefinierten AuthenticationStateProvider, indem Sie die Anleitung im Abschnitt Implementieren eines benutzerdefinierten AuthenticationStateProvider weiter oben in diesem Artikel befolgen. Wenn Sie die Anleitung in diesem Abschnitt bereits befolgt haben, ersetzt der folgende CustomAuthStateProvider den in diesem Abschnitt gezeigte.

Die folgende CustomAuthStateProvider-Implementierung macht eine benutzerdefinierte Methode (AuthenticateUser) verfügbar, um einen Benutzer anzumelden und Consumer über die Änderung des Authentifizierungsstatus zu benachrichtigen.

CustomAuthStateProvider.cs:

using System.Security.Claims;
using Microsoft.AspNetCore.Components.Authorization;

public class CustomAuthStateProvider : AuthenticationStateProvider
{
    public override Task<AuthenticationState> GetAuthenticationStateAsync()
    {
        var identity = new ClaimsIdentity();
        var user = new ClaimsPrincipal(identity);

        return Task.FromResult(new AuthenticationState(user));
    }

    public void AuthenticateUser(string userIdentifier)
    {
        var identity = new ClaimsIdentity(
        [
            new Claim(ClaimTypes.Name, userIdentifier),
        ], "Custom Authentication");

        var user = new ClaimsPrincipal(identity);

        NotifyAuthenticationStateChanged(
            Task.FromResult(new AuthenticationState(user)));
    }
}

Hinweis

Der vorangehende Code, der eine neue ClaimsIdentity erstellt, verwendet die mit C# 12 (.NET 8) eingeführte vereinfachte Initialisierung der Auflistung. Weitere Informationen finden Sie unter Sammlungsausdrücke – C#-Sprachreferenz.

In einer Komponente:

  • Der Angreifer kann AuthenticationStateProvider einschleusen.
  • Fügen Sie ein Feld hinzu, das den Bezeichner des Benutzers enthält.
  • Fügen Sie eine Schaltfläche und eine Methode hinzu, um den AuthenticationStateProvider in CustomAuthStateProvider umzuwandeln und AuthenticateUser mit dem Bezeichner des Benutzers aufzurufen.
@inject AuthenticationStateProvider AuthenticationStateProvider

<input @bind="userIdentifier" />
<button @onclick="SignIn">Sign in</button>

<AuthorizeView>
    <Authorized>
        <p>Hello, @context.User.Identity?.Name!</p>
    </Authorized>
    <NotAuthorized>
        <p>You're not authorized.</p>
    </NotAuthorized>
</AuthorizeView>

@code {
    public string userIdentifier = string.Empty;

    private void SignIn()
    {
        ((CustomAuthStateProvider)AuthenticationStateProvider)
            .AuthenticateUser(userIdentifier);
    }
}

Der oben beschriebene Ansatz kann erweitert werden, um Benachrichtigungen über Authentifizierungsstatusänderungen über einen benutzerdefinierten Dienst auszulösen. Die folgende CustomAuthenticationService-Klasse verwaltet den Anforderungsprinzipal von aktuellen Benutzenden in einem Sicherungsfeld (currentUser) mit einem Ereignis (UserChanged), das der Authentifizierungsstatus-Anbieter abonnieren kann, wobei das Ereignis NotifyAuthenticationStateChanged aufruft. Mit der zusätzlichen Konfiguration weiter unten in diesem Abschnitt kann CustomAuthenticationService in eine Komponente mit Logik eingefügt werden, die festlegt, dass der CurrentUser das UserChanged-Ereignis auslöst.

CustomAuthenticationService.cs:

using System.Security.Claims;

public class CustomAuthenticationService
{
    public event Action<ClaimsPrincipal>? UserChanged;
    private ClaimsPrincipal? currentUser;

    public ClaimsPrincipal CurrentUser
    {
        get { return currentUser ?? new(); }
        set
        {
            currentUser = value;

            if (UserChanged is not null)
            {
                UserChanged(currentUser);
            }
        }
    }
}

Registrieren Sie in der Program-Datei CustomAuthenticationService im Dependency-Injection-Container zum Einfügen von Abhängigkeiten:

builder.Services.AddScoped<CustomAuthenticationService>();

Registrieren Sie in Startup.ConfigureServices von Startup.cs den CustomAuthenticationService im Abhängigkeitsinjektionscontainer:

services.AddScoped<CustomAuthenticationService>();

Registrieren Sie in der Program-Datei CustomAuthenticationService im Dependency-Injection-Container zum Einfügen von Abhängigkeiten:

builder.Services.AddSingleton<CustomAuthenticationService>();

Der folgende CustomAuthStateProvider abonniert das CustomAuthenticationService.UserChanged-Ereignis. Die GetAuthenticationStateAsync-Methode gibt den Authentifizierungsstatus des Benutzenden zurück. Zunächst basiert der Authentifizierungsstatus auf dem Wert von CustomAuthenticationService.CurrentUser. Wenn die Benutzenden wechseln, wird für die neuen Benutzenden ein neuer Authentifizierungsstatus (new AuthenticationState(newUser)) für Aufrufe von GetAuthenticationStateAsync erstellt:

using Microsoft.AspNetCore.Components.Authorization;

public class CustomAuthStateProvider : AuthenticationStateProvider
{
    private AuthenticationState authenticationState;

    public CustomAuthStateProvider(CustomAuthenticationService service)
    {
        authenticationState = new AuthenticationState(service.CurrentUser);

        service.UserChanged += (newUser) =>
        {
            authenticationState = new AuthenticationState(newUser);
            NotifyAuthenticationStateChanged(Task.FromResult(authenticationState));
        };
    }

    public override Task<AuthenticationState> GetAuthenticationStateAsync() =>
        Task.FromResult(authenticationState);
}

Die SignIn-Methode der folgenden Komponente erstellt einen Anspruchsprinzipal für den Bezeichner des Benutzers, der auf CustomAuthenticationService.CurrentUser festgelegt werden soll:

@using System.Security.Claims
@inject CustomAuthenticationService AuthService

<input @bind="userIdentifier" />
<button @onclick="SignIn">Sign in</button>

<AuthorizeView>
    <Authorized>
        <p>Hello, @context.User.Identity?.Name!</p>
    </Authorized>
    <NotAuthorized>
        <p>You're not authorized.</p>
    </NotAuthorized>
</AuthorizeView>

@code {
    public string userIdentifier = string.Empty;

    private void SignIn()
    {
        var currentUser = AuthService.CurrentUser;

        var identity = new ClaimsIdentity(
            [
                new Claim(ClaimTypes.Name, userIdentifier),
            ],
            "Custom Authentication");

        var newUser = new ClaimsPrincipal(identity);

        AuthService.CurrentUser = newUser;
    }
}

Hinweis

Der vorangehende Code, der eine neue ClaimsIdentity erstellt, verwendet die mit C# 12 (.NET 8) eingeführte vereinfachte Initialisierung der Auflistung. Weitere Informationen finden Sie unter Sammlungsausdrücke – C#-Sprachreferenz.

Zusätzliche Ressourcen