skip to Main Content

Before posting this question I’ ve done lots of research in the Internet, I’ ve found some stuff, but I wasn’t able to find something that fits my case.
So please provide me the right direction or code snippets to go on.

I’m developing an app in .NET 6 which consists of 2 projects: Blazor WASM project for the client-side and a WEB-API project for the API’s of my app.

At the moment, I’ve successfully implemented authentication from a central Identity Server 4. I receive "id_token" and "access_token" and use them to
secure access to my web-APIs from unauthenticated users.

The problem is that now I want to implement "role-based authorization". The facts are:

  • I cannot modify the code of the common Identity Server I use.
  • I have the users, the roles and their connection inside my app’s database.

I think that the right solution here is implementing a MIDDLEWARE which reads the roles from my database and adds them into the "Claims".

Where should I develop the middleware? Web-Api project, blazor project or both???

If I developed a middleware in the Web-Api project (where by default there is already a pipeline) which adds roles into the Claims of "access_token",
the blazor project wouldn’t work bacause of the modified token, right???

Could you help me with code snippets or provide me the right directions?

Thank you for your time!!!

2

Answers


  1. Authorization is solely an API responsibility:

    • The Blazor app sends up an access token to identify the user, via the subject claim
    • The API verifies the JWT on every request, then looks up other claims for that subject
    • The extra claims can be cached for subsequent requests with the same access token

    My sample .NET API shows one way of doing this and building a custom ClaimsPrincipal. Once you’ve done that, .NET’s standard authorization techniques such as the [Authorize] attribute will work based on the ClaimsPrincipal’s contents.

    Login or Signup to reply.
  2. The client sends the access_token in every request. The server validates the access_token and then creates a ClaimsPrincipal with the claims that were included in the token. In your server can add additional claims to the ClaimsPrincipal using the OnTokenValidated event. Example:

    .AddJwtBearer("Bearer", options =>
    {
        options.Events = new JwtBearerEvents
        {
            OnTokenValidated = async context =>
            {
                var user = context.Principal;
                var userId = user.FindFirstValue(ClaimTypes.NameIdentifier);
    
                // Get DbContext. If you don't use Entity Framework request your own data access service.
                //var dbContext = context.HttpContext.RequestServices.GetRequiredService<AppDbContext>();
    
                // Retrieve user roles from database and create a list of role claims.
                var claims = new List<Claim>
                {
                    new Claim(ClaimTypes.Role, "admin")
                };
    
                var claimsIdentity = new ClaimsIdentity(claims);
    
                user.AddIdentity(claimsIdentity);
                await Task.CompletedTask;
            }
        };
    });
    

    Then in your controllers you can check for the role using [Authorize(roles = "admin")] or User.IsInRole("admin");.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search