Search code examples
asp.net-coreasp.net-identityjwtclaims-based-identity

How to implement the same claim for different departments


I am building a webapp that uses windows authentication and supplements it with roles and claims from a local DB. I am planning to use a JWT to store this information once the user is authenticated.

Our organization has different departments and I am wondering how I could go about implementing roles/claims in this case.

For example:

Bob is an admin for both department A and B.

In Bob's principle, how could I add claims that reflect this. I.E.

bob.claims = new claim[] {

    new claim() { department = "A", role = Roles.Admin },
    new claim() { department = "B", role = Roles.Admin }
}

Then I could do something like:

[Authorize(IsInDepartmentRole(Department: "A", Role: Roles.Admin)]

Keep in mind this is all pseudo-code.

I realize storing this info in a JWT might not work out, so I am willing to move to an in memory cache (or similar).

How can I accomplish this?


Solution

  • You can add this information as claims, but since a claim consists of a type-value, the approach in the pseudo code will not work.

    There are some options, but I would suggest the following:

    new Claim { Type = "DepartmentRole", Value = "A;Admin" }
    

    In any case, keep the type a constant. The value can be split into A and Admin, corresponding to department and role. You can add multiple claims of the same type.

    Now you can define a policy:

    services.AddAuthorization(options =>
    {
        options.AddPolicy("AdminOfDeptA", policy => 
                                          policy.RequireClaim("DepartmentRole", "A;Admin"));
    }
    

    The authorize attribute only allows strings as parameter, so again your pseudocode won't work. But you can now use this, where AdminOfDeptA is the configured policy:

    [Authorize("AdminOfDeptA")]
    

    If you don't want to define all combinations, you may want to take a look at resource-based authorization.