Search code examples
c#asp.net-coreasp.net-core-mvcasp.net-core-identity

Checking roles with ASP:Net Identity 2.1 does not work


I upgraded my ASP.Net MVC Core application from 1.1 to 2.1 including migrating ASP.Net Identity from 1.1 to 2.1.

I got the things working including ASP.Net Identity EntityFramework integration using Sqlite.

My startup.cs configuration looks like this:

        services.AddDefaultIdentity<IdentityUser>()
            .AddEntityFrameworkStores<ApplicationDbContext>();

        services.Configure<IdentityOptions>(options =>
        {
            // Password settings.
            options.Password.RequireDigit = true;
            options.Password.RequireLowercase = true;
            options.Password.RequireNonAlphanumeric = true;
            options.Password.RequireUppercase = true;
            options.Password.RequiredLength = 6;
            options.Password.RequiredUniqueChars = 1;

            // Lockout settings.
            options.Lockout.DefaultLockoutTimeSpan = TimeSpan.FromMinutes(5);
            options.Lockout.MaxFailedAccessAttempts = 5;
            options.Lockout.AllowedForNewUsers = true;

            // User settings.
            options.User.AllowedUserNameCharacters =
            "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-._@+";
            options.User.RequireUniqueEmail = false;
        });

        services.AddAuthentication()
            .AddMicrosoftAccount(options =>
            {
                options.ClientId = Configuration["Authentication:Microsoft:ClientId"];
                options.ClientSecret = Configuration["Authentication:Microsoft:ClientSecret"];
            });

        services.AddAuthorization(options =>
        {
            options.AddPolicy(PolicyNames.RequireTauchbold, policy => policy.RequireRole(Rolenames.Tauchbold));
        });

And in Configure() I have:

app.UseAuthentication();

Then in my controller I have:

[Authorize(Policy = PolicyNames.RequireTauchbold)]
public class EventController : Controller
{
    ...

The entire source-code can be found here on GitHub.

Problem

The problem is that the above check on the controller always return "access denied" even if I am properly logged in and have the role assigned. I don't know that can go wrong here. Do anybody have an idea what I could miss here?

Update

I figured, that the plain, empty [Authorize] attribute works (enforces the login) but the [Authorize(Policy = '...')] does not recognise the role. I've checked the db tables but they look good to me. Do I needs to configure anything else in the database beside ÀspNetUsers, AspNetRoles and AspNetUserRoles ?

Update 2:

I got it work with the solution from @itminus but had to add a call to AddDefaultUI() in the startup to get the Login and Register working again. So my startup now contains these lines to configure Identity:

        services.AddIdentity<IdentityUser, IdentityRole>()
            .AddRoleManager<RoleManager<IdentityRole>>()
            .AddDefaultUI()
            .AddEntityFrameworkStores<ApplicationDbContext>();

Solution

  • I've just tested your code . Since AddDefaultIdentity<IdentityUser>() in the version of 2.1.x won't enable Role by default , I change your code as below :

    //services.AddDefaultIdentity<IdentityUser>()
    //    .AddEntityFrameworkStores<ApplicationDbContext>();
    
    services.AddIdentity<IdentityUser, IdentityRole>()
        .AddRoleManager<RoleManager<IdentityRole>>()
        .AddEntityFrameworkStores<ApplicationDbContext>();
    

    To test with the above code , I register a new user and add the role for the user :

    await _roleManager.CreateAsync(new IdentityRole(Rolenames.Tauchbold));
    var user= await _userManager.GetUserAsync(HttpContext.User);
    await _userManager.AddToRoleAsync(user, Rolenames.Tauchbold);
    

    And sign out firstly and sign in again , it works now :

    enter image description here