I can't get permissions that a role has defined in my access_token.
I defined 3 roles (with Keycloak): ADMIN, GUEST and SUPERADMIN.
SUPERADMIN has read, write and gestion permissions (p_Read, p_Write and p_gestion).
With postman, SUPERADMIN do login, and gets the obfuscated access_token.
When I deobfuscate it, I get the following information (which is correct)
"iat": 1654784756,
"jti": "6bc716df-66fc-47ad-9eaf-8ef252969c61",
"iss": "https://dev.mydomain.com/auth/realms/Licenses",
"aud": "account",
"sub": "55552ce7-3f92-49a7-835f-7cd356a34d7e",
"typ": "Bearer",
"azp": "Licenses",
"session_state": "1cb9ac94-0d53-423c-9cd6-66472c8ce02b",
"acr": "1",
"realm_access": {
"roles": [
"SUPERADMIN",
"offline_access",
"default-roles-licenses",
"uma_authorization"
]
},
"resource_access": {
"Licenses": {
"roles": [
"SUPERADMIN"
]
},
"account": {
"roles": [
"manage-account",
"manage-account-links",
"view-profile"
]
}
},
"scope": "openid email profile",
"email_verified": false,
"name": "Pepe",
"preferred_username": "pepe#user.com",
"given_name": "Pepe",
"family_name": "Pepe",
"email": "pepe#user.com"
but, I don't receive the permissions configured for SUPERADMIN. I need to receive the "p_Read","p_Write" and "p_Gestion" permissions in my access_token.
Am I missing some setting or am I doing something wrong?
You can get attributes by Get role API.
Also user needs the "manage-realm" role when you get the token.
Steps
Assign "manage-realm" to user
Get Token
Get Role
Related
I have an Azure bot that we are using to build a message extension functionality in Microsoft Teams.
Users access it via the conversation feature in team channel. It works by taking a search string entered by a user in the message extension, searching our database for matching entries, and once an entry is selected posting a message into a team channel linking to the resource.
It is working as expected in all environments except for Production, where we see the following behaviour:
Some search strings return the expected ("nothing found") response
But most search strings return a 502 error. The bot's log says "The bot is not part of the conversation roster"
We are sideloading the manifest for the bot and its associated tab app. As far as I can tell, there are no differences in bot or app setup between Production and the other apps we setup (QA, staging, etc)
I've checked the other SO posts and those on the Microsoft PowerUsers forum. They mostly say that the bot needs to be added to Teams in Azure, but this has been done. And it's working for all of our environments except for Production...
This is the manifest. It references the eduMe app already published in AppSource:
{
"$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.11/MicrosoftTeams.schema.json",
"manifestVersion": "1.11",
"version": "1.1.3",
"id": "28beac77-2765-4248-8a25-02779d7242ca",
"packageName": "com.microsoft.teams.extension",
"developer": {
"name": "eduMe",
"websiteUrl": "https://edume.com",
"privacyUrl": "https://edume.com",
"termsOfUseUrl": "https://edume.com"
},
"icons": {
"color": "resources/edume-hexamark.png",
"outline": "resources/edume-outline-hexamark.png"
},
"name": {
"short": "eduMe Beta_test2",
"full": "eduMe Beta_test2"
},
"description": {
"short": "Giving the deskless workforce seamless access to relevant knowledge",
"full": "Training your workforce doesn't need to be painful. No more clunky authoring tools and dated, desktop based learning. eduMe helps you deliver the training when and where your workforce need it."
},
"accentColor": "#F3F3FF",
"bots": [
{
"botId": "e9aa4df6-ed17-423f-bb7a-5cb1f6f090d7",
"scopes": ["personal", "team", "groupchat"],
"supportsFiles": false,
"isNotificationOnly": true
}
],
"composeExtensions": [
{
"botId": "29b96f25-2032-4fa4-8abd-5ac8f652699f",
"commands": [
{
"id": "searchQuery",
"context": ["compose", "commandBox"],
"description": "Command to search courses.",
"title": "Search",
"type": "query",
"parameters": [
{
"name": "searchQuery",
"title": "Search Query",
"description": "Your search query",
"inputType": "text"
}
]
}
]
}
],
"configurableTabs": [
{
"configurationUrl": "https://edume-ms-teams.herokuapp.com/index.html#/config",
"canUpdateConfiguration": true,
"scopes": ["team", "groupchat"]
}
],
"staticTabs": [
{
"entityId": "index",
"name": "Home",
"contentUrl": "https://edume-ms-teams.herokuapp.com/index.html#/tab",
"websiteUrl": "https://edume-ms-teams.herokuapp.com/index.html#/tab",
"scopes": ["personal"]
}
],
"permissions": ["identity", "messageTeamMembers"],
"validDomains": [
"localhost",
"*.microsoftonline.com",
"*.herokuapp.com",
"*.botframework.com",
"edume.com"
],
"webApplicationInfo": {
"id": "29b96f25-2032-4fa4-8abd-5ac8f652699f",
"resource": "api://edume-ms-teams.herokuapp.com/29b96f25-2032-4fa4-8abd-5ac8f652699f"
}
}
I'm testing Teams Messaging Extension for Search-based commands. After creating solution with "YO TEAMS" and creating BOT in Azure with BotId / AppId and password / Secret. And put these as values in .env file in solution.
By running the command "gulp ngrok-serve" I get ngrok url generated and things look like it should be fine. But by uploading a .zip file from the package folder in Teams, I get the error message "Unable to reach app, Please try again".
Just to test, I have created another solution with only "Tab". And I get almost the same error message when I try to upload .zip,
"There was a problem reaching this app"
There are many frustrating tutorials some old and some new. By running the command "gulp ngrok-serve" you start ngrok for tunnel. And ngrok URL that is generated seems to work:
And the URL is stored as an endpoint for BOT in Azure:
So what have I missed here since it does not work?
Here is my manifest file:
{
"$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.6/MicrosoftTeams.schema.json",
"manifestVersion": "1.6",
"id": "{{APPLICATION_ID}}",
"version": "{{VERSION}}",
"packageName": "{{PACKAGE_NAME}}",
"developer": {
"name": "gonadn consulting",
"websiteUrl": "https://{{HOSTNAME}}",
"privacyUrl": "https://{{HOSTNAME}}/privacy.html",
"termsOfUseUrl": "https://{{HOSTNAME}}/tou.html"
},
"name": {
"short": "TeamsMsgExtSearch",
"full": "TeamsMsgExtSearch"
},
"description": {
"short": "TODO: add short description here",
"full": "TODO: add full description here"
},
"icons": {
"outline": "icon-outline.png",
"color": "icon-color.png"
},
"accentColor": "#D85028",
"configurableTabs": [],
"staticTabs": [],
"bots": [],
"connectors": [],
"composeExtensions": [
{
"botId": "{{MICROSOFT_APP_ID}}",
"canUpdateConfiguration": false,
"commands": [
{
"id": "msgSearchCommandMessageExtension",
"title": "MsgSearchCommand",
"description": "Add a clever description here",
"initialRun": true,
"parameters": [
{
"name": "parameter",
"description": "Description of the parameter",
"title": "Parameter"
}
],
"type": "query"
}
]
}
],
"permissions": [
"identity",
"messageTeamMembers"
],
"validDomains": [
"{{HOSTNAME}}"
],
"showLoadingIndicator": false
}
Link to Git Repo
I am very new to spring boot in pivotal cloud foundry. I am able to deploy the apps and bind them to config-server. When i access the app, it is asking for login details. I tried with pivotal credentials it didn't worked. I am struggling from days to find the credentials for this. Can someone help where can i find the username and password.
I have checked VCAP_SERVICES env variable but no luck. Below is my VCAP_SERVICES
{
"VCAP_SERVICES": {
"p-config-server": [
{
"binding_name": null,
"credentials": {
"access_token_uri": "https://p-spring-cloud-services.uaa.run.pivotal.io/oau
th/token",
"client_id": "p-config-server-066a4553-a934-4d52-b016-30e2ab7e6d90",
"client_secret": "rHnPwJj613pP",
"uri": "https://config-da1be911-4c82-41a3-a3bd-0b06ea295480.cfapps.io"
},
"instance_name": "config-server",
"label": "p-config-server",
"name": "config-server",
"plan": "trial",
"provider": null,
"syslog_drain_url": null,
"tags": [
"configuration",
"spring-cloud"
],
"volume_mounts": []
}
],
"p-service-registry": [
{
"binding_name": null,
"credentials": {
"access_token_uri": "https://p-spring-cloud-services.uaa.run.pivotal.io/oau
th/token",
"client_id": "p-service-registry-ae9f69cf-258d-45ea-821e-1fa4db37f1a3",
"client_secret": "XJOLKHZqwssd",
"uri": "https://eureka-89a144f4-7dc7-4b6d-8152-c4414b748ec0.cfapps.io"
},
"instance_name": "service-registry",
"label": "p-service-registry",
"name": "service-registry",
"plan": "trial",
"provider": null,
"syslog_drain_url": null,
"tags": [
"eureka",
"discovery",
"registry",
"spring-cloud"
],
"volume_mounts": []
}
]
}
}
{
"VCAP_APPLICATION": {
"application_id": "1b398fd8-61f2-47e3-875d-d3fe7574513a",
"application_name": "customer-service",
"application_uris": [
"customer-service-demo.cfapps.io"
],
"application_version": "d0243f11-b7af-4bb3-b3a3-b7a4c95e6298",
"cf_api": "https://api.run.pivotal.io",
"limits": {
"disk": 1024,
"fds": 16384,
"mem": 1024
},
"name": "customer-service",
"organization_id": "8e425cae-75a0-433a-a8a7-79c4f81d7c85",
"organization_name": "MSA_springboot",
"process_id": "1b398fd8-61f2-47e3-875d-d3fe7574513a",
"process_type": "web",
"space_id": "8902b90c-9964-4f9d-b426-ca1635589ebe",
"space_name": "development",
"uris": [
"customer-service-demo.cfapps.io"
],
"users": null,
"version": "d0243f11-b7af-4bb3-b3a3-b7a4c95e6298"
}
}
User-Provided:
SPRING_PROFILES_ACTIVE: dev
No running env variables have been set
No staging env variables have been set```[enter image description here][1]
[1]: https://i.stack.imgur.com/9kNWC.png
I have been trying to host bot which works on local to the Azure Hosting.
I'm trying to connect hosted bot with local emulator gives connection error (emulator :Cannot post activity. Unauthorized).
My .bot file:
{
"name": "production",
"description": "",
"services": [
{
"type": "endpoint",
"appId": "********************",
"appPassword": "*************",
"endpoint": "intermediatorbotsample2019.azurewebsites.net/api/messages",
"name": "AzureAccountLive",
"id": "178"
}
],
"padlock": "",
"version": "2.0",
"path": "D:\\Architecture\IntermediatorBot\\production.bot",
"overrides": null
}
I took a look at your bot file in your comment. The problem is that you have "name": "AzureAccountLive" in your services section. This name MUST be "production". The outer level "name" has to match the name of the bot (in this case, it's probably intermediatorbotsample2019). It's the Name:Production, Type:Endpoint combination that ABS looks for. If you update your botfile to match what I have below, your bot should work as expected.
{
"name": "YOURBOTNAMEHERE",
"description": "",
"services": [
{
"type": "endpoint",
"appId": "********************",
"appPassword": "*************",
"endpoint": "http://intermediatorbotsample2019.azurewebsites.net/api/messages",
"name": "production",
"id": "178"
}
],
"padlock": "",
"version": "2.0",
"path": "D:\\Architecture\IntermediatorBot\\production.bot",
"overrides": null
}
Re genreted AppId and secret from https://dev.botframework.com/.
Previously was using AzureBotProject replaced it with AzureBotChannelProject instead.
I have a JHipster monolithic app with oauth2 running Keycloak locally.
I don't know how exactly should jhipster work with oauth2... first I thought it would create the user automatically, but it didn't, so I configured keycloak: I created the jhipster realm, the web_app client, the client roles ROLE_ADMIN and ROLE_USER, and the users admin and user with their correct roles.
The problem is that when I login as admin it is not being recognized as ROLE_ADMIN, as a result I cannot access the administrator menu. So I started looking through the code, trying to understand how Jhipster receives the credentials from Keycloak, and I realized that the OAuth2Authentication object in AccountResource.java does not bring the ROLE_ADMIN, but the ROLE_USER which I don't understand why. The OAuth2Authentication object in json looks like this:
{
"authorities": [
{
"authority": "ROLE_USER"
}
],
"details": {
"remoteAddress": "0:0:0:0:0:0:0:1",
"sessionId": "rkkveY_Xa5zFFd0SKu9Of_FLGRnbdiTPHdnpj4gc",
"tokenValue": "eyJhbGciOiJSUzI1...",
"tokenType": "bearer",
"decodedDetails": null
},
"authenticated": true,
"userAuthentication": {
"authorities": [
{
"authority": "ROLE_USER"
}
],
"details": {
"sub": "f348bbbb-9441-4543-9940-9da31e50d877",
"email _verified": true,
"name": "Admin Administrator",
"preferred_username": "admin",
"given_name": "Admin",
"family_name": "Administrator",
"email": "admin#localhost"
},
"authenticated": true,
"principal": "Admin Administrator",
"credentials": "N/A",
"name": "Admin Administrator"
},
"clientO nly": false,
"principal": "Admin Administrator",
"oauth2Request": {
"clientId": "web_app",
"scope": [
],
"requestParameters": {
},
"resourceIds": [
],
"authorities": [
],
"approved": true,
"refresh": false,
"redirectUri": null,
"responseTypes": [
],
"extensions": {
},
"grantType": null,
"refreshTok enRequest": null
},
"credentials": "",
"name": "Admin Administrator"
}
here is the yo-rc.json:
{
"generator-jhipster": {
"promptValues": {
"packageName": "xxxxxxxxxxx"
},
"jhipsterVersion": "5.7.2",
"applicationType": "monolith",
"baseName": "XXXXXXXXXX",
"packageName": "xxxxxxxxxxxxxx",
"packageFolder": "xxxxxxxxxxxxxx",
"serverPort": "8080",
"authenticationType": "oauth2",
"cacheProvider": "ehcache",
"enableHibernateCache": true,
"websocket": false,
"databaseType": "sql",
"devDatabaseType": "h2Disk",
"prodDatabaseType": "mysql",
"searchEngine": false,
"messageBroker": false,
"serviceDiscoveryType": false,
"buildTool": "maven",
"enableSwaggerCodegen": false,
"clientFramework": "angularX",
"useSass": false,
"clientPackageManager": "npm",
"testFrameworks": [],
"jhiPrefix": "jhi",
"otherModules": [],
"enableTranslation": false
}
}
How can I fix this?
In keycloak administration go to Clients >> YOUR_CLIENT >> Mappers -> Add new mapper -> Set mapper type to "User client Role" and "Token claim name" set to "authorities" and Claim JSON Type to string.
New Solution
You can see more in the link below the configuration of Keycloak, so it sends the roles in the token and we don't need to change the original code.
https://medium.com/#mobilegotop/how-to-configure-keycloak-for-jhipster-a-spring-boot-app-with-roles-709491e0b5c6
Old solution.
Not working so well, because the ROLES are not coming in the normal grant privileges
In UserService.java I changed like this:
public UserDTO getUserFromAuthentication(final AbstractAuthenticationToken authToken) {
Map<String, Object> attributes;
if (authToken instanceof OAuth2AuthenticationToken) {
attributes = ((OAuth2AuthenticationToken) authToken).getPrincipal().getAttributes();
} else if (authToken instanceof JwtAuthenticationToken) {
attributes = ((JwtAuthenticationToken) authToken).getTokenAttributes();
} else {
throw new IllegalArgumentException("AuthenticationToken is not OAuth2 or JWT!");
}
User user = getUser(attributes);
JSONArray auths = (JSONArray) attributes.get("authorities");
Set<Authority> authorities = new HashSet<Authority>();
for(int i=0; i<auths.size(); i++){
Authority au = new Authority();
au.setName(auths.get(i).toString());
authorities.add(au);
}
user.setAuthorities(authorities);
return new UserDTO(syncUserWithIdP(attributes, user));
}
and set the "authorities" in the token Claim Name like:
I had the same issue, I guess this is because Keycloak gives the client roles in another claim "resource_access" and Spring Boot Security Oauth2 library doesn't read the roles here.
I have modified UserService.java to try at first to read this claim and the sub value corresponding to the clientId by decoding the JWT token, this is cleaner because it reads the client roles only.
public UserDTO getUserFromAuthentication(OAuth2Authentication authentication) {
OAuth2AuthenticationDetails oauth2AuthenticationDetails = (OAuth2AuthenticationDetails) authentication
.getDetails(); // should be an OAuth2AuthenticationDetails
Map<String, Object> details = (Map<String, Object>) authentication.getUserAuthentication().getDetails();
User user = getUser(details);
String tokenValue = oauth2AuthenticationDetails.getTokenValue();
DecodedJWT jwt = JWT.decode(tokenValue);
Map<String, Object> resourceAccessClaim = jwt.getClaim("resource_access").asMap();
String clientId = authentication.getOAuth2Request().getClientId();
if (resourceAccessClaim.containsKey(clientId)) {
((Map<String, Object>) resourceAccessClaim.get(clientId)).values().forEach(rn -> {
user.setAuthorities(extractAuthorities((List<String>) rn));
});
}
if (user.getAuthorities() == null || user.getAuthorities().size() == 0) {
user.setAuthorities(extractAuthorities(authentication, details));
}
// convert Authorities to GrantedAuthorities
Set<GrantedAuthority> grantedAuthorities = user.getAuthorities().stream().map(Authority::getName)
.map(SimpleGrantedAuthority::new).collect(Collectors.toSet());
...