Delen via


Eenvoudige autorisatie in ASP.NET Core

Autorisatie in ASP.NET Core wordt beheerd met het kenmerk [Authorize] en de verschillende parameters. In de meest eenvoudige vorm, het toepassen van het kenmerk [Authorize] op een controller, actie of Razor Pagina, beperkt de toegang tot dat onderdeel voor geverifieerde gebruikers.

Voorwaarden

In dit artikel wordt ervan uitgegaan dat u basiskennis hebt van ASP.NET Core Razor Pages en MVC. Als u nog niet eerder ASP.NET Core hebt gebruikt, raadpleegt u de volgende bronnen:

Het kenmerk [Authorize] gebruiken

De volgende code beperkt de toegang tot de AccountController voor geverifieerde gebruikers:

[Authorize]
public class AccountController : Controller
{
    public ActionResult Login()
    {
    }

    public ActionResult Logout()
    {
    }
}

Als u autorisatie wilt toepassen op een actie in plaats van op de controller, past u het kenmerk AuthorizeAttribute toe op de actie zelf:

public class AccountController : Controller
{
   public ActionResult Login()
   {
   }

   [Authorize]
   public ActionResult Logout()
   {
   }
}

Nu hebben alleen geverifieerde gebruikers toegang tot de functie Logout.

U kunt ook het kenmerk AllowAnonymous gebruiken om toegang door niet-geverifieerde gebruikers toe te staan voor afzonderlijke acties. Bijvoorbeeld:

[Authorize]
public class AccountController : Controller
{
    [AllowAnonymous]
    public ActionResult Login()
    {
    }

    public ActionResult Logout()
    {
    }
}

Dit zou alleen geverifieerde gebruikers toestaan in AccountController, met uitzondering van de actie Login, die toegankelijk is voor iedereen, ongeacht of ze geverifieerd zijn of niet/een anonieme status hebben.

Waarschuwing

[AllowAnonymous] omzeilt autorisatieverklaringen. Als u [AllowAnonymous] en een [Authorize] kenmerk combineert, worden de [Authorize] kenmerken genegeerd. Als u bijvoorbeeld [AllowAnonymous] toepast op controllerniveau:

  • Autorisatievereisten van [Authorize] attributen op dezelfde controller of actiemethoden op de controller worden genegeerd.
  • Authenticatie-middleware wordt niet overgeslagen, maar hoeft niet te slagen.

De volgende code beperkt de toegang tot de LogoutModelRazor-pagina voor geverifieerde gebruikers:

[Authorize]
public class LogoutModel : PageModel
{
    public async Task OnGetAsync()
    {

    }

    public async Task<IActionResult> OnPostAsync()
    {

    }
}

Zie Geverifieerde gebruikers vereisenvoor informatie over het globaal vereisen van verificatie van alle gebruikers.

Kenmerk en Razor Pagina's autoriseren

De AuthorizeAttribute kan niet worden toegepast op Razor pagina-handlers. [Authorize] kan bijvoorbeeld niet worden toegepast op OnGet, OnPostof een andere pagina-handler. Overweeg het gebruik van een ASP.NET Core MVC-controller voor pagina's met verschillende autorisatievereisten voor verschillende handlers. Een MVC-controller gebruiken wanneer er verschillende autorisatievereisten vereist zijn:

  • Is de minst complexe benadering.
  • Is de methode die door Microsoft wordt aanbevolen.

Als u besluit geen MVC-controller te gebruiken, kunnen de volgende twee benaderingen worden gebruikt om autorisatie toe te passen op Razor Methoden voor pagina-handler:

  • Gebruik afzonderlijke pagina's voor pagina-handlers waarvoor verschillende autorisatie is vereist. Gedeelde inhoud verplaatsen naar een of meer gedeeltelijke weergaven. Indien mogelijk is dit de aanbevolen aanpak.

  • Voor inhoud die een gemeenschappelijke pagina moet delen, schrijft u een filter dat autorisatie uitvoert als onderdeel van IAsyncPageFilter.OnPageHandlerSelectionAsync. In het PageHandlerAuth GitHub-project ziet u deze aanpak:

    [TypeFilter(typeof(AuthorizeIndexPageHandlerFilter))]
    public class IndexModel : PageModel
    {
        private readonly ILogger<IndexModel> _logger;
    
        public IndexModel(ILogger<IndexModel> logger)
        {
            _logger = logger;
        }
    
        public void OnGet()
        {
    
        }
    
        public void OnPost()
        {
    
        }
    
        [AuthorizePageHandler]
        public void OnPostAuthorized()
        {
    
        }
    }
    
    public class AuthorizeIndexPageHandlerFilter : IAsyncPageFilter, IOrderedFilter
    {
        private readonly IAuthorizationPolicyProvider policyProvider;
        private readonly IPolicyEvaluator policyEvaluator;
    
        public AuthorizeIndexPageHandlerFilter(
            IAuthorizationPolicyProvider policyProvider,
            IPolicyEvaluator policyEvaluator)
        {
            this.policyProvider = policyProvider;
            this.policyEvaluator = policyEvaluator;
        }
    
        // Run late in the selection pipeline
        public int Order => 10000;
    
        public Task OnPageHandlerExecutionAsync(PageHandlerExecutingContext context, PageHandlerExecutionDelegate next) => next();
    
        public async Task OnPageHandlerSelectionAsync(PageHandlerSelectedContext context)
        {
            var attribute = context.HandlerMethod?.MethodInfo?.GetCustomAttribute<AuthorizePageHandlerAttribute>();
            if (attribute is null)
            {
                return;
            }
    
            var policy = await AuthorizationPolicy.CombineAsync(policyProvider, new[] { attribute });
            if (policy is null)
            {
                return;
            }
    
            await AuthorizeAsync(context, policy);
        }
    
        #region AuthZ - do not change
        private async Task AuthorizeAsync(ActionContext actionContext, AuthorizationPolicy policy)
        {
            var httpContext = actionContext.HttpContext;
            var authenticateResult = await policyEvaluator.AuthenticateAsync(policy, httpContext);
            var authorizeResult = await policyEvaluator.AuthorizeAsync(policy, authenticateResult, httpContext, actionContext.ActionDescriptor);
            if (authorizeResult.Challenged)
            {
                if (policy.AuthenticationSchemes.Count > 0)
                {
                    foreach (var scheme in policy.AuthenticationSchemes)
                    {
                        await httpContext.ChallengeAsync(scheme);
                    }
                }
                else
                {
                    await httpContext.ChallengeAsync();
                }
    
                return;
            }
            else if (authorizeResult.Forbidden)
            {
                if (policy.AuthenticationSchemes.Count > 0)
                {
                    foreach (var scheme in policy.AuthenticationSchemes)
                    {
                        await httpContext.ForbidAsync(scheme);
                    }
                }
                else
                {
                    await httpContext.ForbidAsync();
                }
    
                return;
            }
        }
    

Waarschuwing

De voorbeeldbenadering PageHandlerAuthniet:

  • Opstellen met autorisatiekenmerken die zijn toegepast op de pagina, het paginamodel of wereldwijd. Het opstellen van autorisatiekenmerken resulteert in dat verificatie en autorisatie meerdere keren worden uitgevoerd wanneer er meerdere AuthorizeAttribute- of AuthorizeFilter-instanties op de pagina zijn toegepast.
  • Werk in combinatie met de rest van ASP.NET Core-verificatie- en autorisatiesysteem. U moet controleren of het gebruik van deze methode correct werkt voor uw toepassing.

Er zijn geen plannen om de AuthorizeAttribute op Razor pagina-handlers te ondersteunen.