9
votes

I have setup authentication with keycloak 4.1 successfully. Now I am setting up authorization.

NOTE:

Post might seem longer than it actually is as it contains lot of images that show configuration. Also already referred following SO posts:

wildfly integration with keycloak 403 forbidden error

403 Forbidden error, while access the ClientRepresentation in keycloack

Keycloak 403 (Forbidden) on Keycloak.loadUserProfile()

Facing 403 Forbidden error

wildfly integration with keycloak 403 forbidden error

UPDATE:

I created another resource (i.e. undeleted default resource which gets auto created) with /*, and now 403 is not seen. But when I put a debugger in my application, I see that only this resource is present in the permissions list:

AuthorizationContext authzContext =  keycloakSecurityContext.getAuthorizationContext();
java.util.List<Permission> pems = authzContext.getPermissions();

It contains only default resource i.e resource with /* , when it should contain the resource test_role_resource in the list as well. (in case the above configuration matches the permission,policy,role of user getting authentciated)

(Original Post) Issue:

With all the configuration(shared below), when I test using the evaluate option under authorization tab, result is permit:

enter image description here

But when I make a request to this resource through postman, I get 403.

enter image description here


CONFIGURATION:

1. Following the documentation, I created a realm role : role_special_user and created a user : user_special with this role and role user.

2. Next, my resource server / client is as shown below with full scope enabled:

enter image description here

3. Under authorization tab, I created a resource as shown below:

enter image description here enter image description here

4. The role based policy is :

enter image description here

and is mapped to resource using following permission:

enter image description here

5. Now, keycloak json is:

{
  "realm": "demo12",
  "auth-server-url": "http://localhost:8180/auth",
  "ssl-required": "none",
  "resource": "server12",
  "credentials": {
    "secret": "XXXXXXX"
  },
  "confidential-port": 0,
  "policy-enforcer": {}
}

6. And Keycloak Jetty adapter configuration is:

final String KEYCLOAK_JSON = Constants.KC_CONFIG_JSON_PATH;         
InputStream is = Thread.currentThread().getContextClassLoader().getResourceAsStream(KEYCLOAK_JSON);
AdapterConfig keyCloakConfig;
ObjectMapper mapper = new ObjectMapper(new SystemPropertiesJsonParserFactory());
mapper.setSerializationInclusion(JsonInclude.Include.NON_DEFAULT);          
keyCloakConfig = mapper.readValue(is, AdapterConfig.class);

KeycloakJettyAuthenticator kcAuthenticator = new KeycloakJettyAuthenticator();
keyCloakAuthenticator.setAdapterConfig(keyCloakConfig);
if(kcAuthenticator != null) {
    ConstraintSecurityHandler securityHandler = new ConstraintSecurityHandler();
    ConstraintMapping constraintMapping = new ConstraintMapping();
    constraintMapping.setPathSpec("/*");
    Constraint constraint = new Constraint();           
    constraint.setAuthenticate(true);
    constraint.setRoles(new String[]{"**"});
    constraintMapping.setConstraint(constraint);
    securityHandler.addConstraintMapping(constraintMapping);            
    securityHandler.setAuthenticator(kcAuthenticator);
    context.setSecurityHandler(securityHandler);
}

7. Also, the decoded jwt token sample is:

{
  "jti": "XXXXXXX",
  "exp": 1533798704,
  "nbf": 0,
  "iat": 1533798404,
  "iss": "http://localhost:8180/auth/realms/demo12",
  "aud": "server12",
  "sub": "XXXXXXX",
  "typ": "Bearer",
  "azp": "server12",
  "auth_time": 1533798404,
  "session_state": "XXXXXX",
  "acr": "1",
  "allowed-origins": [],
  "realm_access": {
    "roles": [
      "role_special_user",
      "offline_access",
      "uma_authorization",
      "user"
    ]
  },
  "resource_access": {
    "server12": {
      "roles": [
        "uma_protection"
      ]
    },
    "account": {
      "roles": [
        "manage-account",
        "manage-account-links",
        "view-profile"
      ]
    }
  },
  "scope": "openid email profile",
  "email_verified": false,
  "preferred_username": "user_special"
}

Which part of configuration is wrong which is leading to 403 error?

1
Do you get a stackstrace or error somewhere besides the obvious 403? This is hard to debug without any error messages, I'd go for the ssl configuration via truststore as a gut feeling, but this needs to be verified by some log output. - fl0w
@fl0w The logs should come on keycloak server , right? I am currently running everything on localhost, can SSL still be an issue? - tryingToLearn
What does KeycloakJettyAuthenticator kcAuthenticator = KeyCloakConfig; mean? What is KeyCloakConfig? It looks like it shouldn't even compile. - banan3'14
Why are you inconsistent with KeyCloak version: you said you use version 4.1, but the link to the docs you provided points to version 4.2. Which version then? 4.1 or 4.2? - banan3'14

1 Answers

1
votes

This can be happened due to two reasons mainly,

  1. If you are running the Keycloak locally please check your user has the relevant access. As an example, assume your 'admin' user needed a CLIENT ROLE "view-users" of CLIENT "realm-management" to be able to get information about users. So check whether you have added this role mappings to your user.

2.If you have host your Keycloak in some server, Keep in mind that Keycloak now defaults to HTTPS for all external IP addresses.Till you are getting the SSL certificate to your server disable it in realm setting.

Access to db instance(Here I used PostgresQL)

docker exec -it /bin/bash

Then execute

psql -U YOUR_DB_USER -d YOUR_DB

Execute below command to check realm table.

select * from realm;

In realm table, ssl_required is EXTERNAL by default. Set it to NONE

update REALM set ssl_required='NONE' where id = 'YOUR_REALM_NAME';

Restart the keycloak instance and check the result

docker restart CONTAINER_ID