Search code examples
oauthpermissionsidentityserver4

Identity Server - Dynamically update claims based on selection within application


I have an application that uses Identity Server 4 and open id connect for authentication and authorization. I am now in discussion with the system architect that wants to do a few changes when it comes to the handling the user permissions. Within this application, a user can be a part of a single or multiple regions, and within this region the user can be a part of a single or multiple customers. These users have both regional roles, and customer roles. Within each region, a user can (in worst case, but very possible scenarios) be a part of over 150 customers with different roles in each one, which could result in around 2500 permissions in total.

When the user is browsing the application, the person selects different regions and customers that the user is currently browsing. This means, that a user has different permissions within a resource depending on what region/customer it is currently working on. My system architect suggests that these permissions should be stored within the access token being sent to the resource, so that the resource would check if the user is allowed to perform this action for the specified region/customer, and that these permission claims should update when a user changes region and/or customer. My worry is that these permissions seems a bit too dynamic to be handled inside of an access token as these may change multiple times during a user session within the application,

First of all, is it even possible to tell identity server that "User A just selected this region/customer, please update all of the claims in the token to match this region/customer", and if so, how would I pass the information of the currently selected region and customer to the profile service/user info endpoint (without having to model each region/customer as a custom claim)?

Second of all, my worry is that this is too dynamic to be stored in the token as this WILL change multiple times over the user session. Since a user signs into the application itself, and not into each region and customer, my suggestion was that we put this logic inside of the api/resource, so that when a certain request reaches the API, we check against our permissions database or cache too see if the action the user is performing for region and customer the action is. My understanding is that OpenID Connect and OAuth should not really be used in such a way that he is suggesting, but I may be very wrong?

I've read this arcticle by leastprivilege, which seems to address the same issues that I've stated, but my system architect didn't seem as convinced..


Solution

  • PolicyServer is the follow up of the mentioned article.

    I can repeat what is written there, but in short: authorization is hard and permissions should not be part of the access token.

    Unlike authentication, authorization is context specific and operates on different levels. That makes the access token not the best place for permissions. You also have the problem with updating claims, etc.

    Basically the main purpose of IdentityServer is to handle the authentication of the user and global authorization (as in which client has access to which resource).

    For authorization they've created the PolicyServer, where authorization has become a seperate mechanism to add permissions (claims) to the Identity. In the OSS version this is done with local middleware, but in the paid version this is a seperate server.

    The authorization context is based on the client, resource and user. When you use this as the 'key', then you can add claims for this context. Making it very useful in a micro services architecture.

    Also keep in mind that certain authorization can be resource-based. E.g. the existence of a user in the WebsiteAdmin table can imply that the user is a website admin. Or making a document available for the user only when it was created by the user.