I have set up a Asp.Net Core 3.1 Api application which grants the tokens to users.
Users may have multiple roles. The JWT contains these roles under the claim "Role":
Role: ["Finance", "Manager"]
Authentication works, but I am trying to set up authorization, using:
services.AddAuthorization(options =>
{
options.AddPolicy("Admin", policy => policy.RequireRole("Admin"));
});
My problem is this policy has to read the existence of "Admin" which is the part of "Role" claim. How can I make the policy that looks for an element in a claim array? I have tried RequireClaim and also tried to chain it as in policy.RequireClaim("Role").RequireClaim("Admin") to no avail.
I solved it by this overload:
services.AddAuthorization(options =>
{
options.AddPolicy("Admin", policy => policy.RequireClaim("Roles", "Admin"));
});
Related
I'm using Auth0 as an idP, my Service Provider requires that i add a custom attribute in the assertion.
I've tried doing this on the Dashboard. Dashboard > Applications > Applications -> AddOns. Following this article. https://auth0.com/docs/authenticate/protocols/saml/saml-configuration/customize-saml-assertions
I've added my_custom_attr in the mapping object, screenshot below.
However when i 'Debug', my custom attribute isn't showing in the assertion xml and my Service Provider isn't receiving the custom attribute. They're only receiving the default attributes. email, nickname etc
When using Auth0 as a SAML identity provider, you can customize the outgoing claims using mapping. Consider you have the user profile that looks like this:
RAW JSON
{
"user_id": "auth0|qwer-1234-zxcv-0987",
"email": "john.doe#example.com"
"picture": "https://placeholder.img/user",
"name": "John Doe"
}
If you need the picture attribute to be in the outgoing claims, you would do a mapping like this:
"mappings": {
"picture": "http://schemas.auth0.com/picture"
}
Note that the each property name on the left side represents a property in the Auth0 profile. Each "value" on the right side is the name for the resulting SAML attribute in the assertion.
If you don't have a my_custom_attr property in the user profile, this mapping won't work. The workaround is to use an Auth0 Rule to add that value during the user log in time. You can read more about it here.
Here's an example.
function customizeMappings(user, context, callback) {
// we are altering the user profile
user.my_custom_attr = "My Custom Attribute";
context.samlConfiguration.mappings = {
"http://schemas.xmlsoap.org/ws/2005/05/identity/claims/color": "my_custom_attr"
};
callback(null, user, context);
}
Note that using context.samlConfiguration.mappings in a Rule will override the configuration you've set in your SAML add-on. Therefore, all the mappings you set in the add-on will be lost if you're using a Rule to customize the SAML assertions.
I'm migrating my ServiceStack Ormite MVC application to use the JWTAuthProvider for stateless auth. I have this working by authenticating as normal, and setting the returned BearerToken and RefreshToken on a successful auth:
using (var authService = HostContext.ResolveService<AuthenticateService>(ServiceStackRequest))
{
var response = await authService.PostAsync(new Authenticate
{
provider = CredentialsAuthProvider.Name,
UserName = model.UserName,
Password = model.Password,
RememberMe = true,
});
var authResponse = response.GetDto() as AuthenticateResponse;
Response.Cookies.Append("ss-tok", authResponse.BearerToken, new CookieOptions() {...});
Response.Cookies.Append("ss-reftok", authResponse.RefreshToken, new CookieOptions() {...});
}
This appears to work for some users and not for others. The problem seems to be that user accounts with a lot of permissions end up with much larger BearerToken values, some over 4096, so these cannot be set for the ss-tok cookie.
The JWT Auth provider docs provide references to the CreatePayloadFilter and the PopulateSessionFilter, however these are only used when creating a session from a token, not the other way around. I want to filter out items (the permissions in particular) when serializing to a token.
Ideally the permissions would be excluded if there are too many (or always be excluded if that's not possible) and would be lazy-loaded when accessed. This may be possible with a custom AuthUserSession inheriting from the base AuthUserSession that Lazy-loads the Permissions, but I don't know how I could do this without the JWT Provider loading the permissions to serialise too.
JWT only gives the user information and clientId, how can I get ID of the client as shown in the image
I CAN GET CLIENT DETAILS PARTICULARLY ID FROM THIS URL
https://${SERVER_URL}/auth/admin/realms/master/clients?clientId=test
API RESPONSE
{
"id": "12af651d-f6fe-49ef-8e6f-b951a49ff7db", // want to add this id into JWT
"clientId": "test",
"rootUrl": "${authBaseUrl}", ......
}
but I want to save my api call for getting Id
How can I get client information "Id" within jwt?
Now this is showing on the extraction of jwt
{
exp: 1627981808,
iat: 1627974608,
sub: '923666de-0b37-42f0-b694-0491028d0b78', // user Id
typ: 'Bearer',
azp: 'test', // client id
acr: '1',
scope: 'openid email profile',
email_verified: false,
name: 'name123',
preferred_username: 'name123',
given_name: 'name123',
email: 'any_name#gmail.com'
}
Any help/information will be helpful for me.
You should create and deploy a SPI to your keycloak instance. That's a JAR that overrides standard behaviour. There are various SPIs both described in the documentation and as code in GitHub keycloak repo.
With that SPI you can add just about anything to your token. I would suggest not to change anything that exists in the default token as this might impact your OID compatibility.
See more details here and here.
When I am creating a new user by using Keycloak rest API, the application ignores the realmRoles property not assigning the role to the new user.
Here is an exemple
POST: https://localhost:8543/auth/admin/realms/quarkus/users
Body:
{
"username":"alexandre",
"enabled":true,
"emailVerified":true,
"firstName":"Alexandre",
"lastName":"Oliveira",
"email":"alexandreqogmailcom",
"credentials":[
{
"type":"password",
"value":"123456",
"temporary":false
}
],
"realmRoles":[
"user_esc"
],
"access":{
"mapRoles":true
}
Is there a way to resolve this problem or a work around ?
PS: I am using the keycloak version 12.0.1
If you are expecting that with the endpoint:
POST: https://localhost:8543/auth/admin/realms/quarkus/users
it will also create the realm roles, that will not happen, it will not create the Realm roles. To create the Realm roles you either use the Admin Console or you use the endpoint:
POST https://localhost:8543/auth/admin/realms/quarkus/roles
with the payload
{"name":"<ROLE_NAME>","description":"<DESCRIPTION>"}
if it is a non Composite Realm Role.
To assign the Realm Role to the user, after having create the user, call the endpoint:
POST: https://localhost:8543/auth/admin/realms/quarkus/users/<USER_ID>/role-mappings/realm
with the payload
[{"id":"<Role ID>","name":"<Role Name>"}]
The role ID you can get it from:
GET: https://localhost:8543/auth/admin/realms/quarkus/roles/<ROLE_NAME>
and the user ID from :
GET: https://localhost:8543/auth/admin/realms/quarkus/users/?username=<USERNAME>
I have upload the following bash scripts to automatize this process.
I am having trouble extracting UserAccount properties from MembershipReboot in conjunction with Thinktecture IdentityServer. I have both up and running using the Sample repo here: https://github.com/identityserver/IdentityServer3.MembershipReboot
When I request the "openid profile" scope in an Implicit Grant Flow, I am missing a lot of the user account fields such as "given_name, middle_name", etc from the id_token and response from the userinfo endpoint. I understand this is because they need to be assigned in the GetClaimsFromAccount function.
I can see the requestedClaims come into the GetProfileDataAsync() function in the MembershipRebootUserService class and if I hover over the instance of TAccount in GetClaimsFromAccount I can see the Firstname, Lastname, etc properties appearing in the CustomUser dynamic proxy but I can't for the life of me work out how to access them and copy them into the claims collection?
More Info:
I suspect the issue is with this line:
claims.AddRange(userAccountService.MapClaims(account));
It looks like this should be converting the user account properties into claims but I dont get any back.
The way I understand it works is you add an option to your Scope object to return all of the claims for a user. IncludeAllClaimsForUser is the key property.
e.g.
new Scope
{
Enabled = true,
Name = "roles",
Type = ScopeType.Identity,
IncludeAllClaimsForUser = true,
Claims = new List<ScopeClaim>
{
new ScopeClaim("role")
}
}
My request includes the role property as well. This pulled back all the claims for the user from MR for me. My example is with Implicit flow btw.