Skip to main content

OMS Authentication

The OMS API is secured with OAuth2 using the client credentials and grant type. The client application passes the OAuth2 Client ID, Client Secret and grand type to obtain an access token. These credentials are provided by the OMS team. Access token should be passed to each OMS api call as HTTP header Authorization (example: Authorization: Bearer 123456789). Lifetime of token is 5 min (possibly to be changed in future).

Prerequisites​

Before you begin, ensure you have:

  • OAuth grant_type : Provided by the OMS team.
  • Client ID - Provided by the OMS team
  • Client Secret - Provided by the OMS team

For current implementation (IAM-method), token provider URL is same for all non-prod and prod environments. Difference for prod and non-prod (non-prod includes pp, int, st, tr, local) is in the values of ClientId and ClientSecret

Production Server​

  • OAuth2 Well-Known : https://astore-prod.cloud-iam.com/realms/Astore-p2p/.well-known/openid-configuration
  • OAuth2 URL : https://astore-prod.cloud-iam.com/realms/Astore-p2p/protocol/openid-connect/token
  • OAuth grant_type : Provided by the OMS team.
  • OAuth2 Client ID : Provided by the OMS team (client id for prod).
  • OAuth2 Client Secret : Provided by the OMS team (client secret for prod).

Test Server​

  • OAuth2 URL : https://astore-prod.cloud-iam.com/realms/Astore-p2p/protocol/openid-connect/token
  • OAuth grant_type : Provided by the OMS team.
  • OAuth2 Client ID : Provided by the OMS team (client id for preprod).
  • OAuth2 Client Secret : Provided by the OMS team (client secret for preprod).

Authentication Flow​

  1. Obtain an Access Token
    The client sends a POST request with credentials to the OAuth2 token provider to get an access token.

    curl -X POST \
    https://astore-prod.cloud-iam.com/realms/Astore-p2p/protocol/openid-connect/token \
    -H 'Content-Type: application/x-www-form-urlencoded' \
    -d 'grant_type=client_credentials&client_id=<client_id>&client_secret=<client_secret>'
  2. Use Access Token The client uses the access token to authorize the OMS API requests.

    curl -X GET \
    https://oms-api-in01.astoreshop.com/ \
    -H 'Authorization: Bearer <access token>'

How do the authentication works​

First we need to have base URL (also named as well-known-url).

PROD https://astore-prod.cloud-iam.com/realms/Astore-p2p/.well-known/openid-configuration INT, ST, TR, PP https://astore-prod.cloud-iam.com/realms/Astore-p2p/.well-known/openid-configuration

It is a public provider of basic information: supported encrypt algorithms, validator urls, certificate sources, etc

We might interest the next parts of this information:

wellKnownData.issuer - Base URL of provider service (also it is used as name of jwt issuer) wellKnownData.jwks_uri - URL for initializing jwks client - it provides decryption keys wellKnownData.token_endpoint - URL for generating access token wellKnownData.grant_types_supported - List of actions allowed for customer by token

jwt - library which makes parsing auth token, extract fields from token, validate fields and whole token. We are using js lib "jsonwebtoken v9.0.3". See https://www.npmjs.com/package/jsonwebtoken for details

jwks - (JSON Web Key Set, "JWKS") library which provides public and private signature keys to validate/decrypt tokens. We are using js lib "jwks-rsa v3.2.2". See https://www.npmjs.com/package/jwks-rsa for details

Normally, authorization process is working same way for OMS and lambda.

The authentication is simply, we need to call validator library:

jwt.verify( token, // input token string from customer SignKeyProvider, // signing key or function (provider) options, // algorithms, audience, issuer, nonce, etc (see lib documentation https://www.npmjs.com/package/jsonwebtoken) completionCallback // function (error, result) )

Validation result will be received in callback function (callback is passed as argument).

The validator function works by next steps:

  1. extract data from token. If token is valid, we receive some decrypted fields form token:
    • header: service info
    • payload: information about client

header - basic service information for token validator : alg - encryption algorithm : typ - token type (JWT) : kid - key id

payload - user information : exp expired timestamp in seconds : iat created timestamp in seconds : iss token issuer ( url or name) : sid session id : clientId jwt provider client identifier : aud jwt provider client audience

After parsing JWT token, library is trying to check token integrity. To perform this, need to have decryption key. Key is provided as plain text or a custom key-provider function ( passed as an argument of jwt.verity(...) ). In our case we use key-provider. Key provider is working next way:

  • jwks.getSigningKey(kid, callback(key)) // load key by kid (key-id, value from token)
  • key.getPublicKey() // extract text key value from wrapper object After it, jwt is using those decrypt key to check token integrity and if it's valid - return token payload

Successful authorization - means we got no errors, no exceptions, and we receive valid payload in callback in jwt.verify(...)

In case of some problems with authorisation:​

  1. Check that token can be parsed. Use some parser utility ( for example https://www.jwt.io ) to split token into components. you should see all JWT components described above. If parser utility can't parse token it means some problem with token. Possible issues if token cannot be parsed:
    a) token is cut: ensure that whole token string is passed b) some unnecessary whitespaces are added at the beginning or end of token c) token is incorrect (bad configuration of token provider, using obsolete token provider, using not supported algorithm, ets)
  2. if token is parsed well, but oms/lambda cannot validate it. Try next steps: a) check that function jwt.verify(...) is really called b) ensure that crypto algorithm of token is supported ( included in options of jwt.verify ). If it's absent in options - add it. Also check is current version of library supports this algorithm. c) ensure that token field "iss" matches value "issuer" in the options of jwt.verify, also it should match issue in well-known data d) ensure that token field "aud" is matching value "audience" in options of jwt.verify e) check that token is not outated (has enough lifetime to be handled). token.exp - token.iss = lifetime of token in seconds f) check that key-id (token header : field kid) is present and non empty. g) check that well-known data has correct field jwks_uri (url is valid and reachable), and we use exact this value to initialize JWKS h) check that kid field of token is one of values in data, provided jwks_uri (it means kid is valid and recognized value) i) check that we provide real key value to jwt.validate(...) - the key-provider function is called with correct kid and return valid sign key

Refresh Token​

Access tokens expire after a specific period. The client can use the refresh token to get a new access token without requiring re-authentication.

curl -X POST \
https://astore-prod.cloud-iam.com/realms/Astore-p2p/protocol/openid-connect/token \
-H 'Content-Type: application/x-www-form-urlencoded' \
-d 'grant_type=refresh_token&client_id=<client_id>&client_secret=<client_secret>&refresh_token=<refresh_token>'

Test Access​

curl -X GET \
https://oms-api-in01.astoreshop.com/ \
-H 'Authorization: Bearer <access token>'

If you receive a 200 response, with the message

Hello ! Welcome to the Astoreshop OMS API.

this indicates successful authentication.