0
votes

I am writing a cooperative web API with asp.net core 2.1 using postgresql as db. after the user sign in user is given a JWT token that will be use for the front end side authentication (Front end will be implemented with angular 2+). I want to store the user role in JWT and when the user sign In, user role will be read from the db and it will be store (authorize Role) So I will write Roles on the controller method. I want to use the Authorize attribute.

   // Auth Controller
    [HttpGet("GetUsers")]
    [Authorize(Roles = "admin")]
    public ActionResult GetUsers()
    {
        var users = _authRepository.GetUsers();
        return Ok(users);
    }

and Repository.cs

public List<User> GetUsers()
{
    var users = _context.Users.ToList();
    return users;
}

Question: Do I need to write a middleware to read each user role from JWT and a put that role to the Identity Principal Claims? Please share your experince. I will be glad to know your approch.

1
It's not really clear what you're asking here... What have you tried and what isn't working?GPW
I want to manage user role based on JWT token. Do I need a middleware for that.Hidayat Arghandabi
If you use the Microsoft ASPNET Core Jwt library/handlers (System.IdentityModel.Tokens.Jwt) then any Roles claims in the incoming validated JWT will automatically be extracted and populated in the ClaimsPrincipal (?) and available to use with the Authorize(Roles="...")] attribute.programmerj
I did the same and it worked for me thank you I read from the JWT document. Identity Priciples.Hidayat Arghandabi

1 Answers

2
votes

I am glad I solved this question I am sharing the complete middleware. In every request by the user the middleware will check the userRole that is embadded in JWT token middle point xxxx.UserInformation.yyyyy we will take that user information.

public class AuthenticationMiddleware
{
    private readonly RequestDelegate _next;

    // Dependency Injection
    public AuthenticationMiddleware(RequestDelegate next)
    {
        _next = next;
    }

    public async Task Invoke(HttpContext context)
    {
        //Read the Header
        string authHeader = context.Request.Headers["Authorization"];
        // If header is not null
        if (authHeader != null)
        {   //Fixing the start point and end point           
            int startPoint = authHeader.IndexOf(".") + 1;               
            int endPoint = authHeader.LastIndexOf(".");

            var tokenString = authHeader.Substring(startPoint, endPoint - startPoint).Split(".");
            var token = tokenString[0].ToString()+"==";

            var credentialString = Encoding.UTF8
                .GetString(Convert.FromBase64String(token));

            // Splitting the data from Jwt
            var credentials = credentialString.Split(new char[] { ':',',' });

            // Trim this string.
            var userRule = credentials[5].Replace("\"", ""); 
            var userName = credentials[3].Replace("\"", "");

             // Identity Principal
            var claims = new[]
            {
                new Claim("name", userName),
                new Claim(ClaimTypes.Role, userRule),
            };
            var identity = new ClaimsIdentity(claims, "basic");
            context.User = new ClaimsPrincipal(identity);
        } //will move to the next middlware
        await _next(context);
    }


}

Now we need to call this middleware when the application start by goint to Startup.cs

  public void Configure(IApplicationBuilder app, IHostingEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
        }

        // Authorization Middleware
        app.UseMiddleware<AuthenticationMiddleware>();
     //   Other Middleware will come here

        app.UseMvc();


    }
}

Now Go to controller and Put an attribute on Methods.If the Role is admin it will execute the method or else it will return 403 Status Code.

[HttpGet("GetUsers")]
[Authorize(Roles = "admin")]
    public ActionResult GetUsers()
    {
        var users = _authRepository.GetUsers();
        return Ok(users);
    }

I wish this helped for everyone who will Work with Authentication and Authorization using JWT Authentication in asp.net core all versions.