Атрибут Authorize Core Authorize не работает с JWT

Я хочу реализовать JVT-безопасность в ASP.Net Core. На данный момент все, что я хочу сделать, это читать токены-носители в заголовке Authorization и проверять их по моим критериям. Мне не нужно (и не хочу) включать ASP.Net Identity. На самом деле, я стараюсь избегать использования как можно большего количества вещей, которые MVC добавляет, насколько это возможно, если я им действительно не нужен.

Я создал минимальный проект, который демонстрирует проблему. Чтобы увидеть исходный код, просто просмотрите историю изменений. Я ожидал, что этот образец отклонит все запросы для /api/icons, если они не содержат заголовок Authorization HTTP с соответствующим маркером-носителем. Образец фактически разрешает все запросы.

Startup.cs

using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Configuration;
using Microsoft.AspNetCore.Routing;
using Microsoft.IdentityModel.Tokens;
using System.Text;
using System;
using Newtonsoft.Json.Serialization;

namespace JWTSecurity
{
    public class Startup
    {
        public IConfigurationRoot Configuration { get; set; }

        public Startup(IHostingEnvironment env)
        {
            IConfigurationBuilder builder = new ConfigurationBuilder().SetBasePath(env.ContentRootPath);
            Configuration = builder.Build();
        }

        public void ConfigureServices(IServiceCollection services)
        {
            services.AddOptions();
            services.AddAuthentication();
            services.AddMvcCore().AddJsonFormatters(options => options.ContractResolver = new CamelCasePropertyNamesContractResolver());
        }

        public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
        {
            loggerFactory.AddConsole();
            app.UseJwtBearerAuthentication(new JwtBearerOptions
            {
                AutomaticAuthenticate = true,
                AutomaticChallenge = true,
                TokenValidationParameters = new TokenValidationParameters
                {
                    ValidateIssuerSigningKey = true,
                    IssuerSigningKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes("supersecretkey")),
                    ValidateIssuer = false,
                    ValidateAudience = false,
                    ValidateLifetime = true,
                    ClockSkew = TimeSpan.Zero
                }
            });
            app.UseMvc(routes => routes.MapRoute("default", "{controller=Home}/{action=Index}/{id?}"));
        }
    }
}

Контроллеры/IconsController.cs

using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;

namespace JWTSecurity.Controllers
{
    [Route("api/[controller]")]
    public class IconsController : Controller
    {
        [Authorize]
        public IActionResult Get()
        {
            return Ok("Some content");
        }
    }
}

Ответ 1

Нашел его!

Основная проблема в этой строке:

services.AddMvcCore().AddJsonFormatters(options => options.ContractResolver = new CamelCasePropertyNamesContractResolver());

Я заметил, что, переключившись с AddMvcCore() на AddMvc(), авторизация внезапно начала работать! После копания исходного кода ASP.NET, чтобы увидеть, что делает AddMvc(), я понял, что мне нужен второй вызов, IMvcBuilder.AddAuthorization().

services.AddMvcCore()
    .AddAuthorization() // Note - this is on the IMvcBuilder, not the service collection
    .AddJsonFormatters(options => options.ContractResolver = new CamelCasePropertyNamesContractResolver());

Ответ 2

Вы также используете идентификационную проверку подлинности и неявно проверяете аутентификацию cookie. Возможно, вы вошли в систему с идентификационной схемой и вызвали успешную аутентификацию.

Удалите удостоверение подлинности, если оно не требуется (если требуется только проверка подлинности jwt), в противном случае укажите Bearer схему для атрибута Authorize, как показано ниже:

[Authorize(ActiveAuthenticationSchemes = "Bearer")]

Ответ 3

Для тех, кто даже попробовал предварительный просмотр ответов и не смог решить проблему, ниже показано, как эта проблема была решена в моем случае.

[Authorize(AuthenticationSchemes="Bearer")]

Ответ 4

Добавить схемы аутентификации в атрибут Authorize для несущей с Json Web Token [Авторизовать (AuthenticationSchemes = "Носитель" )]