[keycloak-user] create user via java api

Michal Hajas mhajas at redhat.com
Mon Dec 9 04:07:55 EST 2019


Hi John,

Thank you for you feedback. Answers in text below.

On Fri, Dec 6, 2019 at 2:13 PM John Norris <johnnorris-10 at outlook.com>
wrote:

> Hi Michal and Tony,
> I think my confusion lays in the fact that I have an adminuser which is
> defined in the master realm because that was there during keycloak setup.
> Then I added a working realm and working client app. And I added users to
> the working realm and mapped them to a realm based role.
> And I do that by logging on to keycloak via a local browser, I have to use
> the admin user defined in master realm. And then I can create users in the
> working realm and add them to the realm based role.
> And all of that works. When I browse to a protected resource in my Spring
> app, I get redirected to keycloak login and after a successful login with
> an ordinary user, get sent to that resource. Success.
> So I assumed the same approach would work when using the java api. Builder
> object based on the admin user, saying that I would use the working realm
> and the client id. Because I want those new users to be added to the
> working realm, not the master realm.
> But obviously this does not work because the permissions are not right,
> hence the 401 error.
>

I see your confusion. I will quote one section from our documentation which
can help you understand how this works (sorry if you have already seen
this, it is copy&paste from here:
https://www.keycloak.org/docs/latest/server_admin/index.html#_admin_permissions
):

The master realm in Keycloak is a special realm and treated differently
than other realms. Users in the Keycloak master realm can be granted
permission to manage zero or more realms that are deployed on the Keycloak
server. When a realm is created, Keycloak automatically creates various
roles that grant fine-grain permissions to access that new realm. Access to
The Admin Console and Admin REST endpoints can be controlled by mapping
these roles to users in the master realm. It’s possible to create multiple
super users, as well as users that can only manage specific realms.
When you created your working realm, your adminuser was automatically
granted all permissions to manage your working realm. Now when you open
admin console you are logging into client 'security-admin-console' within
'master' realm and you are able to manage it because your adminuser from
master realm is granted all permission he needs to manage that realm.

>
> I have been basing my code on
> https://gist.github.com/thomasdarimont/c4e739c5a319cf78a4cff3b87173a84b.
>
> As an aside, I am finding that that keycloak does not quite add up. For
> instance, I tried to use the self register feature in KC. They works in
> that it adds a user to the working realm but the user is unusable because
> it is not associated with a role. The answer could be to have a default
> role for new users. Or it could be to call some SB app code that added the
> role. Except that there is no post registration feature to redirect to a
> end point to run this code.
>
> You can add default roles on admin console in Roles -> Default Roles. See:
https://www.keycloak.org/docs/latest/server_admin/index.html#_default_roles


> And with the api, the Builder object can have completely the wrong
> information (non existent user, wrong password) and no exception is thrown.
> I realise that permissions can be caught before they are used (eg a user
> can look but not create) so it is only when a non permissible action is
> called that an exception is called. But the wrong authentication?
>
> It looks like that actual authentication is performed in time it is really
needed, in time some request is done, I can't see anything wrong there. If
you think this should be changed, feel free to file a new issue in our
issue tracker. More information here:
https://www.keycloak.org/community.html.



> So does the api have the same workflow as the browser admin?
>

Yes it does. The only difference is that the authentication is performed
prior to request, not when you .build() Keycloak object. However you need
to make sure you are using master realm and client within master realm. If
I understand it correctly, you should do something like that to make admin
client work:

Keycloak keycloak = KeycloakBuilder
                    .builder()
                    .serverUrl(SERVER_URL)
                    .realm(*"master"*)
                    .username(USERNAME)
                    .password(PASSWORD)
                    .clientId(*"admin-cli"*) *// or some other client
within master realm, it is here for authentication purposes*
                    .resteasyClient(new
ResteasyClientBuilder().connectionPoolSize(10).build())
                    .build();

            CredentialRepresentation credentialRepresentation = new
CredentialRepresentation();

credentialRepresentation.setType(CredentialRepresentation.PASSWORD);
            credentialRepresentation.setValue("12345678");

            UserRepresentation userRepresentation = new
UserRepresentation();
            userRepresentation.setUsername(owner.getUserName());
            userRepresentation.setFirstName(owner.getFirstName());
            userRepresentation.setLastName(owner.getSurName());
            userRepresentation.setEnabled(true);

userRepresentation.setCredentials(Arrays.asList(credentialRepresentation));
            keycloak.realm(*"your_working_realm"*
).users().create(userRepresentation);


>
> Regards,
> John
>
> ------ Original Message ------
> From: "Michal Hajas" <mhajas at redhat.com>
> To: "John Norris" <johnnorris-10 at outlook.com>
> Cc: "keycloak-user at lists.jboss.org" <keycloak-user at lists.jboss.org>
> Sent: 06/12/2019 09:33:41
> Subject: Re: [keycloak-user] create user via java api
>
> Have you changed clientId to some from master realm? In testsuite we are
> using "admin-cli" client.
>
> Michal
>
> ------ Original Message ------
> From: "Tony Harris" <Tony.Harris at oneadvanced.com>
> To: "John Norris" <johnnorris-10 at outlook.com>
> Sent: 06/12/2019 09:23:54
> Subject: RE: Re[2]: create user via java api
>
> John, I will tell you what I did when I was playing in this very area. We
> have an app that allows some users to manager users and few other bits and
> pieces in the realm.
>
> We created a confidential client in the realm we want users to be able to
> manage. We did not assign realm management rights to any normal users.
> Instead we used Spring Security to restrict access to functions that allow
> user creation/maintence by saying users with role X can do this. Then we
> used the RestTemplate to obtain a server side bearer token for the service
> account that we enabled when we created the confidential client, the
> service account was assigned the realm management rights and can do the
> required realm management functions within out SpringBoot application.
>
> For us this meant that if any single normal user account was compromised
> or that user tried to gain access to the keycloak console, they could not
> be used to manage the realm.
>
> Back when we did want individual users able to manage a realm the user was
> created in that realm and given the rights based on the relam-management
> client roles.
>
>
>


More information about the keycloak-user mailing list