หมายเหตุ
การเข้าถึงหน้านี้ต้องได้รับการอนุญาต คุณสามารถลอง ลงชื่อเข้าใช้หรือเปลี่ยนไดเรกทอรีได้
การเข้าถึงหน้านี้ต้องได้รับการอนุญาต คุณสามารถลองเปลี่ยนไดเรกทอรีได้
For an introduction to authentication schemes, see Overview of ASP.NET Core Authentication: Authentication scheme.
In some scenarios, such as Single Page Applications (SPAs), it's common to use multiple authentication methods. For example, the app may use cookie-based authentication to sign a user into an app and establish their identity and Bearer authentication (often relying on JWTs) for JavaScript-based requests to web API endpoints. In some cases, the app may have multiple instances of an authentication handler. For example, an app has two cookie handlers, where one contains a basic identity and one is created when a multi-factor authentication (MFA) is triggered. MFA may be triggered because the user requested an operation that requires extra security.
For the following AddAuthentication call without a default authentication scheme specified, two authentication handlers are added to the app using their default authentication scheme names:
- Cookie (scheme name: "Cookies"): AddCookie
- JWT bearer (scheme name: "Bearer"): AddJwtBearer
builder.Services.AddAuthentication()
.AddCookie(options =>
{
options.LoginPath = "/Account/Unauthorized/";
options.AccessDeniedPath = "/Account/Forbidden/";
})
.AddJwtBearer(options =>
{
options.Audience = "http://localhost:5001/";
options.Authority = "http://localhost:5000/";
});
services.AddAuthentication()
.AddCookie(options => {
options.LoginPath = "/Account/Unauthorized/";
options.AccessDeniedPath = "/Account/Forbidden/";
})
.AddJwtBearer(options => {
options.Audience = "http://localhost:5001/";
options.Authority = "http://localhost:5000/";
});
Specifying the default scheme when calling AddAuthentication results in setting the HttpContext.User property to a ClaimsPrincipal that relies on that identity. If this behavior isn't desired, invoke the parameterless form of AddAuthentication, as shown in the preceding example.
JWT bearer NuGet package
Several examples in this article rely on API in the Microsoft.AspNetCore.Authentication.JwtBearer NuGet package. The package provides middleware that facilitates JSON Web Token (JWT) authentication, enabling secure authentication for APIs and web services.
Select a scheme with an [Authorize] attribute
An app can specify an authentication handler for Razor components, Minimal API endpoints, controllers, action methods, Razor Pages, and PageModels by passing a comma-delimited list of authentication schemes to the [Authorize] attribute. The attribute specifies the authentication schemes regardless of whether or not a default scheme is configured. In the following example, the Cookies (CookieAuthenticationDefaults.AuthenticationScheme) and Bearer (JwtBearerDefaults.AuthenticationScheme) authentication schemes are set.
Note
The following examples require the following namespaces: Microsoft.AspNetCore.Authorization, Microsoft.AspNetCore.Authentication.Cookies, and Microsoft.AspNetCore.Authentication.JwtBearer.
For a Razor component:
@attribute [Authorize(AuthenticationSchemes =
CookieAuthenticationDefaults.AuthenticationScheme + "," +
JwtBearerDefaults.AuthenticationScheme)]
For a Minimal API endpoint, decorate the constructor with an AuthorizeAttribute to set the schemes:
app.MapGet("/api/data", [Authorize(AuthenticationSchemes =
CookieAuthenticationDefaults.AuthenticationScheme + "," +
JwtBearerDefaults.AuthenticationScheme)] () =>
{
...
});
Alternatively, you can pass the schemes via a custom policy:
app.MapGet("/api/data", () =>
{
...
})
.RequireAuthorization(policy =>
policy.AddAuthenticationSchemes(
CookieAuthenticationDefaults.AuthenticationScheme + "," +
JwtBearerDefaults.AuthenticationScheme));
For an MVC controller:
[Authorize(AuthenticationSchemes = AuthSchemes)]
public class MixedAuthSchemesController : Controller
{
private const string AuthSchemes =
CookieAuthenticationDefaults.AuthenticationScheme + "," +
JwtBearerDefaults.AuthenticationScheme;
...
}
For a PageModel class:
[Authorize(AuthenticationSchemes =
CookieAuthenticationDefaults.AuthenticationScheme + "," +
JwtBearerDefaults.AuthenticationScheme)]
public class MixedAuthSchemesModel : PageModel
{
...
}
Authorization middleware approves access with any of the specified schemes in the order listed. If both schemes authenticate the user (a valid cookie and a valid bearer token are present), authorization middleware merges the identities into a single ClaimsPrincipal context.
By specifying a single scheme, the corresponding handler runs. In the following example, only the handler with the Bearer scheme runs, and any cookie-based identities are ignored for the endpoint:
@using Microsoft.AspNetCore.Authorization
@using Microsoft.AspNetCore.Authentication.JwtBearer
@attribute [Authorize(AuthenticationSchemes = JwtBearerDefaults.AuthenticationScheme)]
Select the scheme with an authorization policy
If you prefer to specify the desired schemes in a policy, set the AuthenticationSchemes collection when adding the policy.
In the following example, the Over18 policy only runs against the identity created by the JWT bearer handler (JwtBearerDefaults.AuthenticationScheme). For an example of the MinimumAgeRequirement class used in the following example, see Policy-based authorization in ASP.NET Core. The RequireAuthenticatedUser method enforces user authentication to endpoints where the policy is applied.
Note
The following example requires the Microsoft.AspNetCore.Authentication.JwtBearer namespace.
builder.Services.AddAuthorizationBuilder()
.AddPolicy("Over18", policy =>
{
policy.AuthenticationSchemes.Add(JwtBearerDefaults.AuthenticationScheme);
policy.RequireAuthenticatedUser();
policy.Requirements.Add(new MinimumAgeRequirement(18));
});
builder.Services.AddAuthorization(options =>
{
options.AddPolicy("Over18", policy =>
{
policy.AuthenticationSchemes.Add(JwtBearerDefaults.AuthenticationScheme);
policy.RequireAuthenticatedUser();
policy.Requirements.Add(new MinimumAgeRequirement(18));
});
});
services.AddAuthorization(options =>
{
options.AddPolicy("Over18", policy =>
{
policy.AuthenticationSchemes.Add(JwtBearerDefaults.AuthenticationScheme);
policy.RequireAuthenticatedUser();
policy.Requirements.Add(new MinimumAgeRequirement());
});
});
Use the policy by setting AuthorizeAttribute.Policy.
For a Razor component:
@using Microsoft.AspNetCore.Authorization
@attribute [Authorize(Policy = "Over18")]
For a Minimal API endpoint, call RequireAuthorization with the policy name:
app.MapGet("/api/data", () =>
{
...
})
.RequireAuthorization("Over18");
For a MVC controller:
[Authorize(Policy = "Over18")]
public class RegistrationController : Controller
For a PageModel class:
[Authorize(Policy = "Over18")]
public class MixedAuthSchemesModel : PageModel
{
...
}
[Authorize] attribute scheme and policy scheme interaction
The authorization schemes for an endpoint with one or more Authorize attributes and one or more policy-based schemes are combined to set the final set of permitted schemes for the endpoint. This forms a union, and any listed scheme may authenticate the request. An attribute adding cookies to a policy restricted to Bearer authentication allows a cookie-only request, assuming the cookie creates a ClaimsPrincipal meeting the policy requirements.
Use multiple authentication schemes
Some apps require support for multiple methods of authentication. A typical scenario involves accepting bearer JWTs issued by several identity providers.
Only one JWT bearer handler is registered with the default authentication scheme JwtBearerDefaults.AuthenticationScheme. Register additional JWT bearer schemes for additional identity providers with unique authentication scheme names. The following example names the second scheme "MEID" for the ME-ID issuer.
Note
The following examples require the Microsoft.AspNetCore.Authorization and Microsoft.AspNetCore.Authentication.JwtBearer namespaces.
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer(options =>
{
options.Audience = "https://localhost:5000/";
options.Authority = "https://localhost:5000/identity/";
})
.AddJwtBearer("MEID", options =>
{
options.Audience = "https://localhost:5000/";
options.Authority =
"https://sts.windows.net/00001111-aaaa-2222-bbbb-3333cccc4444/";
});
services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer(options =>
{
options.Audience = "https://localhost:5000/";
options.Authority = "https://localhost:5000/identity/";
})
.AddJwtBearer("MEID", options =>
{
options.Audience = "https://localhost:5000/";
options.Authority =
"https://sts.windows.net/00001111-aaaa-2222-bbbb-3333cccc4444/";
});
Update the default authorization policy to accept both authentication schemes:
var defaultAuthorizationPolicyBuilder = new AuthorizationPolicyBuilder(
JwtBearerDefaults.AuthenticationScheme, "MEID");
defaultAuthorizationPolicyBuilder =
defaultAuthorizationPolicyBuilder.RequireAuthenticatedUser();
builder.Services.AddAuthorizationBuilder()
.SetDefaultPolicy(defaultAuthorizationPolicyBuilder.Build());
builder.Services.AddAuthorization(options =>
{
var defaultAuthorizationPolicyBuilder = new AuthorizationPolicyBuilder(
JwtBearerDefaults.AuthenticationScheme, "MEID");
defaultAuthorizationPolicyBuilder =
defaultAuthorizationPolicyBuilder.RequireAuthenticatedUser();
options.DefaultPolicy = defaultAuthorizationPolicyBuilder.Build();
});
services.AddAuthorization(options =>
{
var defaultAuthorizationPolicyBuilder = new AuthorizationPolicyBuilder(
JwtBearerDefaults.AuthenticationScheme, "MEID");
defaultAuthorizationPolicyBuilder =
defaultAuthorizationPolicyBuilder.RequireAuthenticatedUser();
options.DefaultPolicy = defaultAuthorizationPolicyBuilder.Build();
});
The preceding code configures default authorization with support for multiple authentication schemes:
A new AuthorizationPolicyBuilder initializes a policy builder that accepts authentication from two schemes:
- JwtBearerDefaults.AuthenticationScheme (JWT bearer tokens)
- "MEID" (the custom authentication scheme for ME-ID, defined earlier)
This means users can authenticate using either JWT tokens or the MEID scheme
RequireAuthenticatedUser is called to require authenticated users for access to protected endpoints.
SetDefaultPolicy chained to AddAuthorizationBuilder:
- Registers authorization services.
- Sets this policy as the default for all
[Authorize]attributes that don't specify a custom policy. Any endpoint marked with[Authorize]automatically uses this policy
The result of using the preceding API is that protected endpoints in the app require authentication via either JWT bearer tokens or the MEID scheme, providing flexibility in how users authenticate.
Select a policy scheme based on the Authorization header
For guidance on how to use the AddPolicyScheme method with the ForwardDefaultSelector property to dynamically select an authentication scheme for each request, see Policy schemes in ASP.NET Core.
Additional resources
ASP.NET Core