Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

JWT Authentication .Net core [Authorize] Attribute Ignored by Controller

I'm trying to implement JWT based authentication in my App that has an Angular 8 Frontend and .Net Core Backend. I have added

 app.UseAuthentication();
 app.UseAuthorization();

and

services.AddAuthentication(opt =>

in the startup class.I have decorated the controller method using the [Authorize] attribute. But when i try to hit the controller method without any tokens it allows entry into the controller method.

StartUp

public class Startup
    {
        public Startup(IConfiguration configuration)
        {
     
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            var jwtSettings = Configuration.GetSection("JwtSettings");
            services.AddAuthentication(opt =>
            {
                opt.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                opt.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
            }).AddJwtBearer(options =>
            {
                options.TokenValidationParameters = new TokenValidationParameters
                {
                    ValidateIssuer = true,
                    ValidateAudience = true,
                    ValidateLifetime = true,
                    ValidateIssuerSigningKey = true,
                    ValidIssuer = jwtSettings.GetSection("validIssuer").Value,
                    ValidAudience = jwtSettings.GetSection("validAudience").Value,
                    IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(jwtSettings.GetSection("securityKey").Value))
                };
            });
            services.AddSignalR();

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);

            // In production, the Angular files will be served from this directory
            services.AddSpaStaticFiles(configuration =>
            {
                configuration.RootPath = "ClientApp/dist";
            });

            // requires using Microsoft.Extensions.Options
            services.Configure<DatabaseSettings>(
                Configuration.GetSection(nameof(DatabaseSettings)));

            services.AddSingleton<IDatabaseSettings>(sp =>
                sp.GetRequiredService<IOptions<DatabaseSettings>>().Value);

            services.AddSingleton<FileService>();

            services.AddSingleton<InternalReportService>();


            services.AddTransient<MailService>();
            services.AddMvc(option => option.EnableEndpointRouting = false);


        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            app.UseRouting();
            app.UseMvc();
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Error");
                app.UseHsts();
            }
            app.UseHttpsRedirection();
            app.UseStaticFiles();          
            app.UseAuthentication();
            app.UseAuthorization();             

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapHub<CoreHub>("/corehub");
                endpoints.MapControllerRoute("default", "{controller=Home}/{action=Index}");

            });

            app.UseSpa(spa =>
            {
                  
                spa.Options.SourcePath = "ClientApp";

                if (env.IsDevelopment())
                {
                    spa.UseProxyToSpaDevelopmentServer("http://localhost:4200");

                }
            });
        }
    }

Controller

[Authorize]
public async Task UploadFile(IFormFile file)
{
// Do Stuff
}
like image 934
techno Avatar asked Oct 03 '21 10:10

techno


People also ask

How to create custom authentication handler to validate JWT token?

Create Custom Authentication handler to validate JWT token Get the metadata from the custom authorization server (OAuth) Create .NET Core Project. Create "AuthConfigManager" class. It is used to get the metadata from the authorization server. Add below references to the project using the NuGet package manager.

How does addjwtbearer handle JWT authentication?

The AddJwtBearer will handle all requests and will check for a valid JWT Token in the header. If it is not passed, or the token is expired, it will generate a 401 Unauthorized HTTP response. Next, I am going to implement the authentication manager which will handle authentication of users.

What is the use of authorization attribute in ASP NET Core?

Thank you. Authorization in ASP.NET Core is controlled with AuthorizeAttribute and its various parameters. In its most basic form, applying the [Authorize] attribute to a controller, action, or Razor Page, limits access to that component authenticated users.

How to add JWT helper class in JWT?

The next step is to add JWT Helper class that is used to create a Token and Refresh Token and validation of Token. To add class first create “JwtHelpers” folder in the root project then create a class.


Video Answer


3 Answers

Well, you have configured the authentication part of your API, now you need to configure the authorization the same way...

You can configure like this:

services.AddAuthorization(options =>
{
    options.AddPolicy("Default", new AuthorizationPolicyBuilder()
        .AddAuthenticationSchemes(JwtBearerDefaults.AuthenticationScheme)
        .RequireAuthenticatedUser()
        .Build());

    options.AddPolicy("Admin", new AuthorizationPolicyBuilder()
        .RequireRole("Admin")
        .AddAuthenticationSchemes(JwtBearerDefaults.AuthenticationScheme)
        .RequireAuthenticatedUser()
        .Build());
});

Then you will be able to use the attribute as

[Authorize("User")]
[Authorize("Admin")]

on your controllers or specific endpoints.

If you wish to put this default policy on all your endpoints/controllers and control only the "AllowAnonymous" part of if, you can do this:

services.AddMvc()
        .AddMvcOptions(options =>
        {
            // Mark all endpoints with the default policy
            options.Filters.Add(new AuthorizeFilter("Default"));
        })
like image 65
MestreDosMagros Avatar answered Nov 08 '22 22:11

MestreDosMagros


According to Your authentication scheme, You should specify attribute this way: [Authorize(AuthenticationSchemes = "Bearer")] and this should work as You expect

like image 36
Mateech Avatar answered Nov 08 '22 22:11

Mateech


I usually add DefaultSchema.

services.AddAuthentication(opt =>
{
    opt.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
    opt.DefaultScheme = JwtBearerDefaults.AuthenticationScheme;
    opt.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
//...

and authorization.

services.AddAuthorization(opts =>
{
    opts.DefaultPolicy = new AuthorizationPolicyBuilder(opts.DefaultPolicy)
          .RequireAuthenticatedUser()
//...
like image 20
GibbOne Avatar answered Nov 08 '22 22:11

GibbOne