We want to use the FIWARE IdM, both Keystone and Horizon. Specifically during sign-up we want to
- create a user
- add that user to an organisation
- authorise the user for an application
We have installed Keystone and Horizon using the latest KeyRock docker image on the docker hub (https://hub.docker.com/r/fiware/idm/).
Because the KeyRock web interface creates Cloud organisations, community users in regions like Spain etc i decided to try to use the SCIM API to create and authorize users:
Note: The SCIM API documents (http://docs.keyrock.apiary.io/#reference/scim-2.0) imply the SCIM calls are on the KeyRock server port, however they are available on the Keystone server port. The SCIM documentation would be clearer if it mentioned http://[keystone server]/v3/OS-SCIM/v2/Users/ instead of http://keyrock/v3/OS-SCIM/v2/Users/
Lets say we have an application (SCIM consumer) with application_id=app1. This application is created using the Horizon front-end, or using the
POST /v3/OS-OAUTH2/consumers
call. I am not aware of a difference between the two ways of creating an application although i have not tried the latter yet. This is a one-time operation, so we used the web interface to create the application and associated role.
so we have a role for the application = role1
and we create a user using SCIM
POST /v3/OS-SCIM/v2/Users/
that yields user_id=user1
When i try to authorize him for our application with
PUT /v3/OS-ROLES/users/user1/applications/app1/roles/role1
i get the following error:
{
"error": {
"message": "_check_allowed_to_get_and_assign() got an unexpected keyword argument 'userName'",
"code": 400,
"title": "Bad Request"
}
}
The next step would be to obtain a resource owner token through KeyRock using
POST [KeyStone server]/oauth2/token
But that is moot because of the above error.
Logging into the KeyRock user interface with user1 gives the error:
"You are not authorized for any projects." I assume this is because user1 is not authorized for an organisation. user1 is invisible to other users or the admin in the KeyRock user interface so i cannot assign the necessary authorizations.
Any ideas anyone?
Which roles does user1 still need to have and how to assign them so that KeyRock is satisfied?
After looking deep into your issue, it turns out that it might be related to the lack of the new user's default organization. Even though requests to SCIM API Users endpoint should create only users, it is certain that KeyRock users have internally a default organization, which cannot be seen from the outside. Since it makes sense to create this organization automatically as well, we just made a few improvements in the SCIM controller at KeyRock that take charge of this. You can take a look at the changes in our GitHub repository.
I myself made sure that this should solve your issue, by following the same flow (note that the value of the X-Auth-Token
header is an admin token and that the Host
header should be your Keystone endpoint):
Register a user through SCIM API:
POST /v3/OS-SCIM/v2/Users HTTP/1.1
Host: localhost:5000
Accept: */*
Content-Type: application/json
X-Auth-Token: 6bd914d9976c448a98b83ccaf5931c4e
Content-Length: 55
{
"userName": "foo@foo.bar",
"password": "foobar"
}
Which returns the following response:
HTTP/1.1 201 Created
Vary: X-Auth-Token
Content-Type: application/json
Content-Length: 276
{
"userName": "foo@foo.bar",
"urn:scim:schemas:extension:keystone:2.0": {
"domain_id": "default",
"default_project_id": "c590cea2b37c4f1c9ca94a015837cde9"
},
"active": true,
"id": "foo-foo-bar",
"schemas": [
"urn:scim:schemas:core:2.0",
"urn:scim:schemas:extension:keystone:2.0"
]
}
Authorize the newly created user for the application app1
by assigning them the role role1
:
PUT /v3/OS-ROLES/users/foo-foo-bar/applications/app1/roles/role1 HTTP/1.1
Host: localhost:5000
Accept: */*
Content-Type: application/json
X-Auth-Token: fd817b31444141a7a8a15d6d6afd2078
Which in turn returns the following success response:
HTTP/1.1 204 No Content
Vary: X-Auth-Token
Content-Length: 0
After this, I was finally able to obtain a resource owner OAuth2 token, as you requested (the Authorization
header includes the OAuth2 credentials of app1
).
POST /oauth2/token HTTP/1.1
Host: localhost:8000
Accept: */*
Authorization: Basic 12345678abcdefgh=
Content-Type: application/x-www-form-urlencoded
Content-Length: 56
grant_type=password&username=foo@foo.bar&password=foobar
And the token is at last returned:
HTTP/1.0 200 OK
Vary: Accept-Language, Cookie
Content-Type: application/json
{
"access_token": "JYjCV2H8QNakRPUqqdoAHZmpmD0vgQ",
"token_type": "Bearer",
"expires_in": 3600,
"refresh_token": "snnS8djsYw62aUtl9Szk9BBqti36jF"
}