Compartir a través de


Protección de aplicaciones de Blazor del lado servidor de ASP.NET Core

Nota:

Esta no es la versión más reciente de este artículo. Para la versión actual, consulta la versión .NET 8 de este artículo.

Advertencia

Esta versión de ASP.NET Core ya no se admite. Para obtener más información, consulta la Directiva de soporte técnico de .NET y .NET Core. Para la versión actual, consulta la versión .NET 8 de este artículo.

Importante

Esta información hace referencia a un producto en versión preliminar, el cual puede sufrir importantes modificaciones antes de que se publique la versión comercial. Microsoft no proporciona ninguna garantía, expresa o implícita, con respecto a la información proporcionada aquí.

Para la versión actual, consulte la versión .NET 8 de este artículo.

En este artículo se explica cómo proteger las aplicaciones de Blazor del lado servidor como aplicaciones ASP.NET Core.

Las aplicaciones de Blazor del lado servidor están configuradas para la seguridad, de la misma manera que las aplicaciones ASP.NET Core. Para obtener más información, consulte los artículos disponibles en Temas de seguridad de ASP.NET Core.

El contexto de autenticación solo se establece cuando se inicia la aplicación, es decir, cuando la aplicación se conecta por primera vez a WebSocket. El contexto de la autenticación se mantiene durante la vigencia del circuito. Las aplicaciones vuelven a validar periódicamente el estado de autenticación del usuario cada 30 minutos.

Si la aplicación debe capturar usuarios para servicios personalizados o reaccionar a las actualizaciones del usuario, consulte escenarios de seguridad adicionales del lado servidor de ASP.NET Core Blazor.

Blazor difiere de una aplicación web representada por el servidor tradicional que realiza nuevas solicitudes HTTP con cookies en cada navegación de página. La autenticación se comprueba durante los eventos de navegación. Sin embargo, no se tienen en cuenta las cookies. Las cookies solo se envían al realizar una solicitud HTTP a un servidor, lo cual no sucede cuando el usuario navega en una aplicación de Blazor. Durante la navegación, el estado de la autenticación del usuario se comprueba dentro del circuito de Blazor, que puede actualizar en cualquier momento en el servidor mediante la abstracción del RevalidatingAuthenticationStateProvider.

Importante

No se recomienda implementar un NavigationManager personalizado para lograr la validación de autenticación durante la navegación. Si la aplicación debe ejecutar la lógica de estado de autenticación personalizada durante la navegación, use un AuthenticationStateProvider personalizado.

Nota:

En los ejemplos de código de este artículo se adoptan tipos de referencia que admiten un valor NULL (NRT) y análisis estático de estado NULL del compilador de .NET, que se admiten en ASP.NET Core en .NET 6 o posterior. Al tener como destino ASP.NET Core 5.0 o versiones anteriores, quite la designación de tipo null (?) de los ejemplos del artículo.

Plantilla de proyectos

Cree una nueva aplicación de Blazor del lado servidor siguiendo las instrucciones de Herramienta para ASP.NET Core Blazor.

Después de elegir la plantilla de aplicación del lado servidor y configurar el proyecto, seleccione la autenticación de la aplicación en Tipo de autenticación:

  • Ninguno (predeterminado): no hay autenticación.
  • Cuentas individuales: las cuentas de usuario se almacenan en la aplicación mediante Identity en ASP.NET Core.
  • Ninguno (predeterminado): no hay autenticación.
  • Cuentas individuales: las cuentas de usuario se almacenan en la aplicación mediante Identity en ASP.NET Core.
  • Plataforma de identity de Microsoft: para más información, consulta Autenticación y autorización de ASP.NET Core Blazor.
  • Windows: use la autenticación de Windows.

BlazorIdentityUI (cuentas individuales)

Blazor admite la generación de una interfaz de usuario completa basada en BlazorIdentity al elegir la opción de autenticación para cuentas individuales.

La plantilla de Blazor Web App sirve de andamiaje para el código de Identity para una base de datos de SQL Server. La versión de la línea de comandos usa SQLite e incluye una base de datos de SQLite para Identity.

La plantilla se ocupa de lo siguiente:

  • Agrega componentes IdentityRazor y lógica relacionada para tareas de autenticación rutinarias, como iniciar y cerrar usuarios.
  • Agrega los paquetes y dependencias relacionados con Identity.
  • Hace referencia a los paquetes de Identity en _Imports.razor.
  • Crea una clase de usuario Identity personalizada (ApplicationUser).
  • Crea y registra un contexto de base de datos EF Core (ApplicationDbContext).
  • Configura el enrutamiento para los puntos de conexión integrados Identity.
  • Incluye validación y lógica de negocios de Identity.

Para inspeccionar los componentes Identity del marco Blazor, accede a ellos en las carpetas Pages y Shared de la carpeta Account de la plantilla de proyecto Blazor Web App (origen de referencia).

Al elegir los modos de representación de WebAssembly interactivo o Automático interactivo, el servidor controla todas las solicitudes de autenticación y autorización, y los componentes de Identity representan estáticamente en el servidor en el proyecto principal de Blazor Web App.

El marco proporciona un AuthenticationStateProvider personalizado en los proyectos de servidor y cliente (.Client) para hacer que fluya el estado de autenticación del usuario al explorador. El proyecto de servidor llama a AddAuthenticationStateSerialization, mientras que el proyecto cliente llama a AddAuthenticationStateDeserialization. La autenticación en el servidor en lugar del cliente permite que la aplicación acceda al estado de autenticación durante la representación previa y antes de que se inicialice el runtime de WebAssembly de .NET. Las implementaciones personalizadas de AuthenticationStateProvider usan el servicio de estado de componente persistente (PersistentComponentState) para serializar el estado de autenticación en comentarios HTML y, después, volverlo a leer desde WebAssembly para crear una instancia de AuthenticationState. Para obtener más información, consulta la sección Configuración del método de Blazor Web App.

Solo para las soluciones de Servidor interactivo, IdentityRevalidatingAuthenticationStateProvider (origen de referencia) es un AuthenticationStateProvider de lado servidor que vuelve a validar la marca de seguridad para el usuario conectado cada 30 minutos que se conecta un circuito interactivo.

Al elegir los modos de representación de WebAssembly interactivo o Automático interactivo, el servidor controla todas las solicitudes de autenticación y autorización, y los componentes de Identity representan estáticamente en el servidor en el proyecto principal de Blazor Web App. La plantilla de proyecto incluye una clase PersistentAuthenticationStateProvider (origen de referencia) en el proyecto .Client para sincronizar el estado de autenticación del usuario entre el servidor y el explorador. La clase es una implementación personalizada de AuthenticationStateProvider. El proveedor usa el servicio de estado de componente persistente (PersistentComponentState) para representar previamente el estado de autenticación y conservarlo en la página.

En el proyecto principal de Blazor Web App, el proveedor de estado de autenticación se denomina IdentityRevalidatingAuthenticationStateProvider (origen de referencia) (solo soluciones de interactividad de servidor) o PersistingRevalidatingAuthenticationStateProvider (origen de referencia) (Soluciones de interactividad de WebAssembly o Auto interactividad).

BlazorIdentity depende de las instancias de DbContext no creadas por una fábrica, lo que es intencional porque DbContext es suficiente para que los componentes de Identity de la plantilla del proyecto se representen estáticamente sin admitir la interactividad.

Para obtener una descripción de cómo se aplican los modos de representación interactiva global a los componentes que no son componentes Identity, mientras que al mismo tiempo se aplica SSR estático a los componentes Identity, consulte ASP.NET Core Blazor modos de representación.

Para obtener más información sobre cómo conservar el estado prerrepresentado, consulte Prerrepresentar componentes Razor ASP.NET Core.

Para obtener más información sobre la interfaz de usuario de identidad de BlazorIdentity y orientación sobre cómo integrar inicios de sesión externos a través de sitios web sociales, consulta Novedades de la identity en .NET 8.

Nota:

Los vínculos de la documentación al origen de referencia de .NET cargan normalmente la rama predeterminada del repositorio, que representa el desarrollo actual para la próxima versión de .NET. Para seleccionar una etiqueta de una versión específica, usa la lista desplegable Cambiar ramas o etiquetas. Para obtener más información, consulta Procedimientos para seleccionar una etiqueta de versión de código fuente de ASP.NET Core (dotnet/AspNetCore.Docs #26205).

Administrar el estado de la autenticación en Blazor Web App

Esta sección se aplica a Blazor Web App que adoptan:

  • Cuentas individuales
  • Representación del lado cliente (CSR, interactividad basada en WebAssembly).

Un proveedor de estado de autenticación del lado cliente solo se usa en Blazor y no está integrado con el sistema de autenticación ASP.NET Core. Durante la representación previa, Blazor respeta los metadatos definidos en la página y usa el sistema de autenticación ASP.NET Core para determinar si el usuario está autenticado. Cuando un usuario navega de una página a otra, se usa un proveedor de autenticación del lado cliente. Cuando el usuario actualiza la página (recarga de página completa), el proveedor de estado de autenticación del lado cliente no participa en la decisión de autenticación en el servidor. Dado que el servidor no conserva el estado del usuario, se pierde ningún estado de autenticación mantenido en el lado cliente.

Para solucionar esto, el mejor enfoque es realizar la autenticación en el sistema de autenticación ASP.NET Core. El proveedor de estado de autenticación del lado cliente solo se encarga de reflejar el estado de autenticación del usuario. Los ejemplos de cómo hacerlo con proveedores de estado de autenticación se muestran mediante la plantilla de proyecto de Blazor Web App y se describen a continuación.

En el archivo Program del proyecto de servidor, llame a AddAuthenticationStateSerialization, que serializa la AuthenticationState devuelta por el AuthenticationStateProvider del lado servidor mediante el servicio estado de componente persistente (PersistentComponentState):

builder.Services.AddRazorComponents()
    .AddInteractiveWebAssemblyComponents()
    .AddAuthenticationStateSerialization();

La API solo serializa las notificaciones de rol y nombre del lado servidor para el acceso en el explorador. Para incluir todas las notificaciones, establezca SerializeAllClaims en true en la llamada del lado servidor a AddAuthenticationStateSerialization:

builder.Services.AddRazorComponents()
    .AddInteractiveWebAssemblyComponents()
    .AddAuthenticationStateSerialization(
        options => options.SerializeAllClaims = true);

En el archivoProgram del proyecto del cliente (.Client), llame a AddAuthenticationStateDeserialization, que agrega un AuthenticationStateProvider en el que el AuthenticationState se deserializa desde el servidor mediante AuthenticationStateData y el servicio de estado de componente persistente (PersistentComponentState). Debe haber una llamada correspondiente a AddAuthenticationStateSerialization en el proyecto de servidor.

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

Nota:

Los vínculos de la documentación al origen de referencia de .NET cargan normalmente la rama predeterminada del repositorio, que representa el desarrollo actual para la próxima versión de .NET. Para seleccionar una etiqueta de una versión específica, usa la lista desplegable Cambiar ramas o etiquetas. Para obtener más información, vea Procedimientos para seleccionar una etiqueta de versión de código fuente de ASP.NET Core (dotnet/AspNetCore.Docs #26205).

Scaffolding para Identity

Para obtener más información sobre scaffolding de Identity en un proyecto de aplicación Blazor del lado servidor, consulte Scaffolding de Identity en proyectos de ASP.NET Core.

Scaffolding de Identity a una aplicación de Blazor del lado servidor:

Notificaciones y tokens adicionales de proveedores externos

Para almacenar notificaciones adicionales de proveedores externos, consulte Conservar notificaciones y tokens adicionales en in ASP.NET Core.

Azure App Service en Linux con Identity Server

Al realizar una implementación en Azure App Service en Linux con Identity Server, especifique el emisor de forma explícita. Para más información, consulte Uso de Identity para proteger un back-end de API web para SPA.

Inserción del AuthenticationStateProvider para los servicios con ámbito en un componente

No intente resolver AuthenticationStateProvider dentro de un ámbito personalizado porque dará como resultado la creación de una nueva instancia del AuthenticationStateProvider que no se inicializa correctamente.

Para acceder al AuthenticationStateProvider dentro de un servicio con ámbito en un componente, inserte al AuthenticationStateProvider con la directiva @inject o el atributo [Inject] y páselo al servicio como parámetro. Este enfoque garantiza que la instancia correcta e inicializada del AuthenticationStateProvider se use para cada instancia de aplicación de usuario.

ExampleService.cs:

public class ExampleService
{
    public async Task<string> ExampleMethod(AuthenticationStateProvider authStateProvider)
    {
        var authState = await authStateProvider.GetAuthenticationStateAsync();
        var user = authState.User;

        if (user.Identity is not null && user.Identity.IsAuthenticated)
        {
            return $"{user.Identity.Name} is authenticated.";
        }
        else
        {
            return "The user is NOT authenticated.";
        }
    }
}

Registre el servicio como uno con ámbito. En una aplicación del lado servidor de Blazor, los servicios con ámbito tienen una vigencia igual a la duración del circuito de la conexión de cliente.

En el archivo Program:

builder.Services.AddScoped<ExampleService>();

En Startup.ConfigureServices de Startup.cs:

services.AddScoped<ExampleService>();

En el componente InjectAuthStateProvider siguiente:

InjectAuthStateProvider.razor:

@page "/inject-auth-state-provider"
@inherits OwningComponentBase
@inject AuthenticationStateProvider AuthenticationStateProvider

<h1>Inject <code>AuthenticationStateProvider</code> Example</h1>

<p>@message</p>

@code {
    private string? message;
    private ExampleService? ExampleService { get; set; }

    protected override async Task OnInitializedAsync()
    {
        ExampleService = ScopedServices.GetRequiredService<ExampleService>();

        message = await ExampleService.ExampleMethod(AuthenticationStateProvider);
    }
}
@page "/inject-auth-state-provider"
@inject AuthenticationStateProvider AuthenticationStateProvider
@inherits OwningComponentBase

<h1>Inject <code>AuthenticationStateProvider</code> Example</h1>

<p>@message</p>

@code {
    private string? message;
    private ExampleService? ExampleService { get; set; }

    protected override async Task OnInitializedAsync()
    {
        ExampleService = ScopedServices.GetRequiredService<ExampleService>();

        message = await ExampleService.ExampleMethod(AuthenticationStateProvider);
    }
}

Para más información, consulte las instrucciones de OwningComponentBase en la Inserción de dependencias de Blazor en ASP.NET Core.

Presentación de contenido no autorizado durante la representación previa con un AuthenticationStateProviderpersonalizado

Para evitar mostrar contenido no autorizado, por ejemplo contenido en un componente AuthorizeView, mientras se representa previamente con un elemento AuthenticationStateProvider personalizado, adopte uno de los enfoques siguientes:

  • Deshabilite la representación previa: indique el modo de representación con el parámetro prerender establecido en false en el componente de nivel más alto de la jerarquía de componentes de la aplicación que no sea un componente raíz.

    Nota:

    No se admite la creación de un componente raíz interactivo, como el componente App. Por lo tanto, el componente App no puede deshabilitar la representación previa directamente.

    En el caso de las aplicaciones basadas en la plantilla de proyecto de Blazor Web App, la representación previa se deshabilita normalmente cuando se usa el componente Routes en el componente App (Components/App.razor):

    <Routes @rendermode="new InteractiveServerRenderMode(prerender: false)" />
    

    Además, deshabilite la representación previa para el componente de HeadOutlet:

    <HeadOutlet @rendermode="new InteractiveServerRenderMode(prerender: false)" />
    

    También puede controlar de forma selectiva el modo de representación aplicado a la instancia del componente Routes. Por ejemplo, consulte los modos de representación de ASP.NET Core Blazor.

  • Autenticar al usuario en el servidor antes de que se inicie la aplicación: para adoptar este enfoque, la aplicación debe responder a la solicitud inicial de un usuario con la página o vista de inicio de sesión basada en Identity y evitar las solicitudes a puntos de conexión Blazor hasta que se autentiquen. Para más información, consulte Creación de una aplicación ASP.NET Core con datos de usuario protegidos por autorización. Después de la autenticación, solo se muestra contenido no autorizado en componentes de Razor creados previamente cuando el usuario no está autorizado para ver el contenido.

Administración de Estados de usuario

A pesar de contener la palabra "state" (estado) en el nombre, AuthenticationStateProvider no se usa para almacenar el estado del usuario general. AuthenticationStateProvider indica únicamente el estado de autenticación del usuario a la aplicación, si ha iniciado sesión en ella y el nombre de usuario con el que ha iniciado sesión.

La autenticación usa la misma autenticación ASP.NET Core Identity que Razor Pages y las aplicaciones MVC. El estado de usuario almacenado en la Identity de ASP.NET Core se dirige a Blazor sin agregar código adicional a la aplicación. Siga las instrucciones de los artículos y tutoriales de la Identity de ASP.NET Core para que las características de Identity surtan efecto en los elementos Blazor de la aplicación.

Para obtener instrucciones sobre la administración de estado general fuera de la Identity de ASP.NET Core, consulte: Administración de estado de Blazor en ASP.NET Core.

Abstracciones de seguridad adicionales

Dos abstracciones adicionales participan en la administración del estado de autenticación:

Nota:

Los vínculos de la documentación al origen de referencia de .NET cargan normalmente la rama predeterminada del repositorio, que representa el desarrollo actual para la próxima versión de .NET. Para seleccionar una etiqueta de una versión específica, usa la lista desplegable Cambiar ramas o etiquetas. Para obtener más información, consulta Procedimientos para seleccionar una etiqueta de versión de código fuente de ASP.NET Core (dotnet/AspNetCore.Docs #26205).

Administración del estado de autenticación al cerrar sesión

El Blazor del lado servidor conserva el estado de autenticación del usuario durante la vigencia del circuito, incluidas las pestañas del explorador. Para cerrar la sesión proactiva de un usuario en las pestañas del explorador cuando el usuario cierra sesión en una pestaña, debes implementar un elemento RevalidatingServerAuthenticationStateProvider (origen de referencia) con un elemento RevalidationInterval corto.

Nota:

Los vínculos de la documentación al origen de referencia de .NET cargan normalmente la rama predeterminada del repositorio, que representa el desarrollo actual para la próxima versión de .NET. Para seleccionar una etiqueta de una versión específica, usa la lista desplegable Cambiar ramas o etiquetas. Para obtener más información, vea Procedimientos para seleccionar una etiqueta de versión de código fuente de ASP.NET Core (dotnet/AspNetCore.Docs #26205).

Duración de la validez de la dirección URL de redireccionamiento temporal

Esta sección es aplicable a Blazor Web App.

Usa la opción RazorComponentsServiceOptions.TemporaryRedirectionUrlValidityDuration para obtener o establecer la vigencia de la validez de la protección de datos de ASP.NET Core para las direcciones URL de redirección temporales emitidas por la representación del lado servidor Blazor. Solo se usan transitoriamente, por lo que la duración debe simplemente ser lo suficientemente larga como para que un cliente reciba la dirección URL y comience la navegación a ella. Sin embargo, también debe ser lo suficientemente larga como para permitir la asimetría del reloj entre servidores. El valor predeterminado es cinco minutos.

En el ejemplo siguiente, el valor se extiende a siete minutos:

builder.Services.AddRazorComponents(options => 
    options.TemporaryRedirectionUrlValidityDuration = 
        TimeSpan.FromMinutes(7));

Recursos adicionales