Skip to content

API and Use

Kyle Ferriter edited this page Apr 2, 2018 · 7 revisions

Automated API

A backend app will be able to retrieve tokens with a request like the one below. The authorization header is an api-key generated by the token service on a per-app basis. This should not be called via any client-side code due to the inclusion of secrets. Token values shown are not valid. verify=False is needed due to self-signed cert currently in use:

>>> r = requests.get('https://test.commonsshare.org/token', 
    headers={
        'Authorization':'Basic 6edb5d6cfe47e561ffde0d9f7edbe6e81f984327830eb56d0eed57669f718036'
    }, 
    params={
        'uid':'<user-openid-subject>',
        'provider':'globus',
        'scope':'openid'},
verify=False)

If an application receives a url and redirect their user to it, then wants to wait until the user logs in, it can either poll with the above request, or add 'block':30 to the params. 30 is the value in seconds that the service will block, and can be any positive number up to the max configured in the service.

On success:

>>> r.status_code
200
>>> r.content
'{"access_token": "YjA0YmQyYWIxMjkyNzY2MTA3MDNkNDZiMDlmYTE4MmYwNTg5ZTk0YmZhOWZmMGUzODBkNzNmMzhiNzdkZTBiOAo="}'

On need to re-authenticate the user (either never logged in or could not refresh):

>>> r.status_code
401
>>> r.content
'{"authorization_url": "https://accounts.google.com/o/oauth2/v2/auth?state=5012cf5d4cd98f3135c16bb811c3304dd4807a079eb8887fae380b859ae3f343&nonce=1c6a94388d92596142088e31b6f7f8035ddfcef15c0da8b9f9dcc6188d8c370d&redirect_uri=https://test.commonsshare.org/authcallback&client_id=<omitted>&scope=openid&response_type=code&access_type=offline&login%20consent"}'

On failure due to invalid api-key:

>>> r.status_code
403

On a blocking request for a token which could not be met in the specified timeout:

>>> r.status_code
404

On failure for reason other than need to re-authenticate (malformed request, or internal error):

>>> r.status_code
500 (or anything else)

Manual login:

First you need to generate a login url. Each is unique, and login responses from unrecognized urls will be discarded.

$ curl -k "https://test.commonsshare.org/authorize?provider=globus&scope=openid%20email%20profile"
{"authorization_url": "https://auth.globus.org/v2/oauth2/authorize?nonce=RANDOM_NONCE_STRING&state=<opaque-state-value>&redirect_uri=https://test.commonsshare.org/authcallback&client_id=6b186d5d-c671-4fb3-b8bd-d86b60e4a5e0&scope=openid%20email%20profile&response_type=code&access_type=offline&login%20consent"}

The nonce value in the url is used to map a login callback to a specific user's login request. A client can wait for the login callback to be received (in this case from globus auth) by submitting a blocking request to the service, and providing a timeout and the nonce value to wait for. Currently, knowledge of this nonce value is sufficient to acquire the user's uid/subject id, but no other information like the access_token itself. This ability may be removed in the future once CommonsShare account creation functionality is completed. A global max timeout will also be implemented, after which any login request from the returned url will be treated as invalid.

$ curl -k "https://test.commonsshare.org/subject_by_nonce?block=60&nonce=RANDOM_NONCE_STRING"

When this request is listening for a response, the user can now browse to the 'authorization_url' value from the first curl command. Once the block threshold is received or a login callback is received for that nonce value, curl will return.

On success (value is specific to your user):

{"uid": "01234567-c567-a1b2-abcd-0123456789ab"}

This value must then be set for the irods user that this globus user account will be linked to.

[irods] $ iadmin aua <your-irods-user>  "01234567-c567-a1b2-abcd-0123456789ab"

Now your irods account is linked to a globus account. Next is to tell your irods client to use the OpenID Connect irods plugin. In your ~/.irods/irods_environment.json file, add the following two lines, replacing the scheme and user values if you are using another one already (pam,kerberos,etc). The openid_provider value tells the irods plugin that when it talks to the token microservice, to use the 'globus' provider, which must be configured in the microservice. Additional providers for both OIDC and OAuth2.0 can be configured in the microservice, and it can be extended to handle the specifics of those providers.

{
    ...
    "irods_user_name": "<your-irods-user>",
    "irods_authentication_scheme": "openid",
    "openid_provider": "globus"
}

Now run iinit. You will be presented with a url, which must be browsed to, which establishes your session in iRODS. Note that the timeout on the validity of this url defaults to 60 seconds, after which iRODS will stop accepting it. Upon successful user login at this url, iinit should exit gracefully, and the other icommands should be successfully authenticated as well.

Clone this wiki locally