Gonna +1 this. I am fighting with the same thing in the documentation right now. There is no clear guidance on what you’re supposed to do here.
I’m also using the ASP.NET Core API Quickstart, and it simply doesn’t work as written. First, it neglects to mention that you need to turn on RBAC and the option to include permissions in the access token. Finally got that done, but the HasScopeHandler class is specifically looking for the scope claim, where these come across as permissions.
+1 from me too. I am also incredibly confused. That first thread provides a solution for the poster’s specific scenario, but doesn’t make clear the distinction between scopes and permissions. The behaviour seems really inconsistent.
I am back into this today trying to figure it out also. I tried to email support and didn’t ever get a clear answer. Trying to get an API that can validate the permissions of a M2M app and a user seems like such a simple requirement for Auth0 to fulfill, but it doesn’t work without major hoops to jump through.
I think the answer is to modify their code to first check for permissions, then move on to checking for the scope like they demonstrate. This seems to be working for me. Whether this is the correct approach, I have no idea since they won’t give a clear answer or update example. I’ll keep messing with this.
public class HasScopeHandler : AuthorizationHandler<HasScopeRequirement>
protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, HasScopeRequirement requirement)
// First check for permissions, they may show up in addition to or instead of scopes...
if (context.User.HasClaim(c => c.Type == "permissions" && c.Issuer == requirement.Issuer && c.Value == requirement.Scope))
// This is the Auth0 version, which only checks for scopes instead of permissions.
// If user does not have the scope claim, get out of here
if (!context.User.HasClaim(c => c.Type == "scope" && c.Issuer == requirement.Issuer))
// Split the scopes string into an array
var scopes = context.User.FindFirst(c => c.Type == "scope" && c.Issuer == requirement.Issuer).Value.Split(' ');
// Succeed if the scope array contains the required scope
if (scopes.Any(s => s == requirement.Scope))
We introduced TOKEN_DIALECT which helps to get the scopes in the Access Token based on the permissions assigned to the user either directly or through roles.
When the RBAC feature is enabled along with token dialect for an API, the permissions which are allowed for the user and requested by the application will be inserted in the scope attribute of the issued Access Token.
An app may request one or more permissions for a specific API. E.g let’s say I have an API with the API identifier named https://myblogapi and the associated permissions read:posts , update:posts and delete:posts.
My blog application only needs read:posts and update:posts so it asks for them in the scope attribute.
Let’s say Alice has an admin role that allows her to have all of the above permissions. When Alice clicks on the login button, my blog redirects Alice’s browser to the Universal Login with the above URL.
When Alice logs in, as she has all of the requested permissions, the Access Token will have both read:posts and updata:posts permissions in the scope but not the delete:posts.
However let’s say Bob is a regular user who has only the permission to read the posts so he has the read:posts permission, so the same URL above will issue an Access Token with read:posts permission only for him.