ASP.NET Core 2.0将Cookie和承载授权结合在一起,用于同一端点

我在VS17中使用“Web应用程序(模型 – 视图 – 控制器)”模板和“.Net Framework”+“ASP.NET Core 2”作为配置创建了一个新的ASP.NET核心Web应用程序项目。 身份validation配置设置为“个人用户帐户”。

我有以下示例端点:

[Produces("application/json")] [Route("api/price")] [Authorize(Roles = "PriceViwer", AuthenticationSchemes = "Cookies,Bearer")] public class PriceController : Controller { public IActionResult Get() { return Ok(new Dictionary { {"Galleon/Pound", "999.999" } ); } } 

"Cookies,Bearer"是通过连接CookieAuthenticationDefaults.AuthenticationSchemeJwtBearerDefaults.AuthenticationScheme

目标是能够为端点配置授权,以便可以使用令牌和cookie身份validation方法访问它。

以下是我在Startup.cs中进行身份validation的设置:

  services.AddAuthentication() .AddCookie(cfg => { cfg.SlidingExpiration = true;}) .AddJwtBearer(cfg => { cfg.RequireHttpsMetadata = false; cfg.SaveToken = true; cfg.TokenValidationParameters = new TokenValidationParameters() { ValidIssuer = Configuration["Tokens:Issuer"], ValidAudience = Configuration["Tokens:Issuer"], IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(Configuration["Tokens:Key"])) }; }); 

因此,当我尝试使用浏览器访问端点时,我得到了一个带有空白html页面的401响应。
我得到了一个空白的html页面的401响应。

然后我登录,当我再次尝试访问端点时,我得到相同的响应。

然后,我尝试通过指定承载令牌来访问端点。 并且返回200响应所需的结果。
并且返回200响应所需的结果。

那么,如果我删除[Authorize(AuthenticationSchemes = "Cookies,Bearer")] ,情况就会相反 – cookievalidation工作并返回200,但是上面使用的相同的承载令牌方法不会给出任何结果而只是重定向到默认的AspIdentity登录页面。

我可以在这里看到两个可能的问题:

1)ASP.NET Core不允许“组合”身份validation。 2)’Cookies’不是有效的模式名称。 但那么使用什么是合适的?

请指教。 谢谢。

我认为您不需要将AuthenticationScheme设置为Controller。 只需在ConfigureServices中使用Authenticated用户,如下所示:

 // requires: using Microsoft.AspNetCore.Authorization; // using Microsoft.AspNetCore.Mvc.Authorization; services.AddMvc(config => { var policy = new AuthorizationPolicyBuilder() .RequireAuthenticatedUser() .Build(); config.Filters.Add(new AuthorizeFilter(policy)); }); 

有关我的资源的文档: registerAuthorizationHandlers

对于该部分,无论scheme-Key是否无效,您都可以使用插值字符串来使用正确的键:

 [Authorize(AuthenticationSchemes = $"{CookieAuthenticationDefaults.AuthenticationScheme},{JwtBearerDefaults.AuthenticationScheme}")] 

编辑:我做了进一步的研究并得出以下结论:不可能使用两个Schemes Or-Like授权方法,但是你可以使用两个公共方法来调用这样的私有方法:

 //private method private IActionResult GetThingPrivate() { //your Code here } //Jwt-Method [Authorize(AuthenticationSchemes = $"{JwtBearerDefaults.AuthenticationScheme}")] [HttpGet("bearer")] public IActionResult GetByBearer() { return GetThingsPrivate(); } //Cookie-Method [Authorize(AuthenticationSchemes = $"{CookieAuthenticationDefaults.AuthenticationScheme}")] [HttpGet("cookie")] public IActionResult GetByCookie() { return GetThingsPrivate(); }