Purpose
Mission Statement
The purpose of this document is to guide developers through a basic implementation of Hosted Login. Further customizations can be made as needed, but are outside the scope of this Quick Start Guide.
Audience
The audience for this document is developers for Akamai Identity Cloud customers who are in the delivery phase for Hosted Login and are ready to get an implementation up-and-running.
This guide assumes the audience is already familiar with:
- Making API calls
- Working with:
- Capture applications
- Capture clients and settings
- Schemas
- Flows
It also assumes the audience has an existing website or app with which to integrate Hosted Login.
Contents
The Quick Start Guide uses an 8-step process to assist you with provisioning and configuring Hosted Login:
- Akamai provides basic elements to enable an implementation of Hosted Login
- Get a token to use in configuration endpoints
- Create a token policy
- Create a login policy
- Create an OIDC client
- Add Capture client settings
- Call Hosted Login from your site/app
- CNAMEs
Step 1: Akamai provides basic elements to enable an implementation of Hosted Login
Schema
Akamai provides a new schema (or adds to an existing schema as appropriate) to include all the attributes necessary for Hosted Login to function properly.
Flow
Akamai provides a new flow built specifically for Hosted Login.
Customer ID
Akamai provides your Hosted Login Customer ID. This is used by all Hosted Login endpoints to point to your core customer account for Hosted Login.
OIDC Configuration Client
Akamai provides the client ID and client secret for your initial OIDC configuration client. This is a confidential client which will have access to all your Hosted Login configuration endpoints.
Step 2: Get a token to use in configuration endpoints
Call the /login/token endpoint to request a token with the API scopes needed for configuration.
When configuring Basic authorization for this call, use your OIDC configuration client ID as the username and the OIDC configuration client secret as the password.
Request Template
curl -X POST \
https://v1.api.<region>.janrain.com/<customer-id>/login/token \
-H 'Authorization: Basic <Base64-encoded-client_id:client_secret>' \
-F 'grant_type=client_credentials' \
-F 'scope=<allowed-config-endpoints>'
Example Request
curl -X POST \
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/login/token \
-H 'Authorization: Basic N2JhNTE2NjEtMWE3ZS0...1BVU1vbGdRRUVLQlpwdlRB' \
-F 'grant_type=client_credentials' \
-F 'scope=*:config/**'
Example Response
{
"access_token": "abc1deA2BfgCDEFhGiHjIJKkL3l4MmnNopOPqQR-Srst-5T6UuvV7WXw8YZx9y0A",
"expires_in": 3600,
"token_type": "Bearer",
"scope": "*:config/**"
}
The scope in this example allows full read/write access to all Hosted Login endpoints for your Customer ID. If you want to limit the scope to a specific endpoint or subset of endpoints, and/or you want to allow only certain actions on those endpoints, you can adjust this value accordingly. Scope formatting is documented here.
Scope Examples
To create a token that can ... | Use this scope syntax |
Read (GET) all token policies, login policies, and OIDC clients | 'scope=.:config/**' |
Read (GET) and configure (POST, PUT) all token policies | 'scope=*:config/tokenPolicies**' |
Read (GET) all token policies and all login policies (separated by a space) | 'scope=.:config/tokenPolicies** .:config/loginPolicies**' |
Read (GET) a specific login policy | 'scope=.:config/loginPolicies/1ab23c45-6789-0123-d4ef-5g678h90ijk1' |
Read (GET) and configure (PUT) a specific login policy | 'scope=*:config/loginPolicies/1ab23c45-6789-0123-d4ef-5g678h90ijk1' |
Read (GET) and configure (PUT) the token policy, login policy, and OIDC client for a specific property (separated by a space) | 'scope=*:config/tokenPolicies/a123bcde-4f56-7890-gh12-i34j567k8l90 *:config/loginPolicies/1ab23c45-6789-0123-d4ef-5g678h90ijk1 *:config/clients/1ab23456-7c8d-90ef-g123-45hij6789012' |
Step 3: Create a token policy
Call the /config/tokenPolicies endpoint using the POST method to create a token policy for your Hosted Login implementation.
When configuring Bearer token authorization for this call, use the configuration token you provisioned in step 2.
Request Template
curl -X POST \
https://v1.api.<region>.janrain.com/<customer-id>/config/tokenPolicies \
-H 'Authorization: Bearer <token> \
-H 'Content-Type: application/json' \
-d '{
"accessTokenLifetime": <lifetime-in-seconds>,
"allowedScopes": [
"<scope>",
"<scope>",
...
],
"refreshTokenLifetime": <lifetime-in-seconds>,
"title": "<new-token-policy-name>"
}'
Example Request
curl -X POST \
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/config/tokenPolicies \
-H 'Authorization: Bearer 123abc456...def789ghi' \
-H 'Content-Type: application/json' \
-d '{
"accessTokenLifetime": 3600,
"allowedScopes": [
"openid",
"profile",
"email",
"address",
"phone"
],
"refreshTokenLifetime": 36000,
"title": "Property 1 Token Policy"
}'
Example Response
"a123bcde-4f56-7890-gh12-i34j567k8l90"
The response contains the ID of the token policy you just created. If you want to review the full token policy you just created, call the /config/tokenPolicies/{token_policy_id} endpoint using the GET method.
Step 4: Create a login policy
Call the /config/loginPolicies endpoint using the POST method to create a login policy for your Hosted Login implementation.
When configuring Bearer token authorization for this call, use the configuration token you provisioned in step 2.
Request Template
curl -X POST \
https://v1.api.<region>.janrain.com/<customer-id>/config/loginPolicies \
-H 'Authorization: Bearer <token> \
-H 'Content-Type: application/json' \
-d '{
"identityStoreDetails": {
"connectionDetails": {
"applicationId": "<capture-app-id>",
"clientId": "<capture-app-owner-client-id>",
"clientSecret": "<capture-app-owner-client-secret>",
"domain": "<provided-by-akamai>",
"entityType": "<entity-type>"
},
"type": "janrainCapture"
},
"loginURL": "https://v1.api.<region>.janrain.com/<customer-id>/auth-ui/login",
"title": "<new-login-policy-name>"
}'
Example Request
curl -X POST \
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/config/loginPolicies \
-H 'Authorization: Bearer 123abc456...def789ghi' \
-H 'Content-Type: application/json' \
-d '{
"identityStoreDetails": {
"connectionDetails": {
"applicationId": "1abcdef2g3hijklmno4pqrs5tu",
"clientId": "abc123defg4h5i67jklmnopqrstuvw89",
"clientSecret": "12a34bc5d67ef8ghij9klmn01o2pqrst",
"domain": "dev-app.janraincapture.com",
"entityType": "user"
},
"type": "janrainCapture"
},
"loginURL": "https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/auth-ui/login",
"title": "Property 1 Login Policy"
}'
Example Response
"1ab23c45-6789-0123-d4ef-5g678h90ijk1"
The response contains the ID of the login policy you just created. If you want to review the full login policy you just created, call the /config/loginPolicies/{login_policy_id} endpoint using the GET method.
Step 5: Create an OIDC client
Call the /config/clients endpoint using the POST method to create an OIDC client for your Hosted Login implementation.
When configuring Bearer token authorization for this call, use the configuration token you provisioned in step 2.
Request Template
curl -X POST \
https://v1.api.<region>.janrain.com/<customer-id>/config/clients \
-H 'Authorization: Bearer <token> \
-H 'Content-Type: application/json' \
-d '{
"loginPolicy": "<login-policy-id>",
"name": "<new-oidc-client-name>",
"redirectURIs": [
"<redirect-uri>"
],
"tokenPolicy": "<token-policy-id>",
"type": "<confidential-or-public>"
}'
Example Request
curl -X POST \
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/config/clients \
-H 'Authorization: Bearer 123abc456...def789ghi' \
-H 'Content-Type: application/json' \
-d '{
"loginPolicy": "1ab23c45-6789-0123-d4ef-5g678h90ijk1",
"name": "Property 1 OIDC Client",
"redirectURIs": [
"https://mydomain.com"
],
"tokenPolicy": "a123bcde-4f56-7890-gh12-i34j567k8l90",
"type": "public"
}'
Example Response
{
"id": "1ab23456-7c8d-90ef-g123-45hij6789012",
"name": "Property 1 OIDC Client",
"redirectURIs": [
"https://mydomain.com"
],
"loginPolicy": "1ab23c45-6789-0123-d4ef-5g678h90ijk1",
"tokenPolicy": "a123bcde-4f56-7890-gh12-i34j567k8l90",
"type": "public",
"_links": {
"self": {
"href": "/config/12345678-1234-1234-1234-123456789012/clients/1ab23456-7c8d-90ef-g123-45hij6789012"
},
"application_client": {
"href": "/config/1abcdef2g3hijklmno4pqrs5tu/clients/abcdefghi12jkl3m4nopqr5stuvwxy67"
}
}
}
The response contains the ID of the OIDC client you just created. If you want to review this client configuration in the future, call the /config/clients/{client_id} endpoint with the GET method.
Note regarding confidential clients. The client secret is returned in the response when you create a confidential client. If you need to access the secret in the future, call the /config/clients/{client_id}/secret endpoint with the GET method.
Step 6: Add Capture client settings
Note. All Example Values in the tables below are examples only. Your values will be different in most cases.
Creating a new OIDC client (in the previous step) automatically creates a Capture login client with the following settings and the appropriate values in place:
Setting Name | Example Value |
janrainOidcClientId | 1ab23456-7c8d-90ef-g123-45hij6789012 |
site_name | Property 1 OIDC Client |
user_entity_type | user |
password_recover_url * | https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/auth-ui/reset-password?client_id=1ab23456-7c8d-90ef-g123-45hij6789012 |
verify_email_url * | https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/auth-ui/verify-account?client_id=1ab23456-7c8d-90ef-g123-45hij6789012 |
* The template for these URLs is: https://v1.api.<region>.janrain.com/<customer-id>/auth-ui/<endpoint>?client_id=<oidc-client-id>
In order for Hosted Login to function, a few more settings must be added to this login client:
Setting Name | Example Value |
default_flow_name | hosted_login_standard |
default_flow_version | 20190808194524428311 |
legal_acceptance_id_1 | terms_of_use_v1 |
legal_acceptance_id_2 | privacy_policy_v1 |
regex_standard_newPassword | .* |
Step 7: Call Hosted Login from your site/app
Before Continuing. There are many OpenID Connect libraries available for use depending on the platform or code of your application. The following examples demonstrate the mechanics of OIDC interactions; however it is recommended that you use a library rather than build from scratch.
Login/Registration
When an end user clicks a login/registration action element on your site or /app (e.g., a Login button), you must make a call to the /login/authorize endpoint to display the Akamai-hosted login page to the user.
The following implementation assumes you’re using a public OIDC client along with PKCE (Proof Key for Code Exchange). This is the recommendation for all end-user facing applications.
Request Template
https://v1.api.<region>.janrain.com/<customer-id>/login/authorize?
client_id=<oidc-client-id>
&redirect_uri=<redirect-uri>
&scope=<oidc-scopes>
&response_type=code
&state=<randomly-generated-state-token>
&code_challenge=<client-generated-string-hashed-and-encoded>
&code_challenge_method=<hashing-algorithm>
Example Request
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/login/authorize?
client_id=1ab23456-7c8d-90ef-g123-45hij6789012
&redirect_uri=https://mydomain.com
&scope=openid profile email phone
&response_type=code
&state=3bd5262737237ef4a
&code_challenge=RTg4QjMyRUJCNzdBRTQ1MkM2NTAzRTVDOEQ5OTg3QjIwMjVBNTcxQTU5RTJFNDYwMzJBQjYxRkM4NjQ0QzdBNw
&code_challenge_method=S256
Making the /login/authorize call displays the Akamai-hosted login page, where the user can sign in or create an account. For example:
Upon successful sign in or account creation, a redirect URI is returned to the app or browser.
Example Redirect URI
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/login/code?
state=security_token%3bd5262737237ef4a
&%url%https://mydomain.com
&code=4JR27W91a-ofgCe9ur2m6bTghy77
Exchange Code for Tokens
Send the authorization code (the code from the redirect URI) to the /login/token endpoint, which exchanges that code for an access token, an identity token, and a refresh token.
The following implementation assumes you’re using a public OIDC client along with PKCE (Proof Key for Code Exchange). This is the recommendation for all end-user facing applications.
Request Template
curl -X POST \
https://v1.api.<region>.janrain.com/<customer-id>/login/token \
-H 'Content-Type: application/x-www-form-urlencoded' \>
-d 'grant_type=authorization_code
&client_id=<oidc-client-id>
&redirect_uri=<redirect-uri>
&code=<code-returned-by-authorize-endpoint>
&code_verifier=<original-client-generated-string>'
Example Request
curl -X POST \
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/login/token \
-H 'Content-Type: application/x-www-form-urlencoded' \
-d 'grant_type=authorization_code
&client_id=1ab23456-7c8d-90ef-g123-45hij6789012
&redirect_uri=https%3A%2F%2Fmydomain.com
&code=4JR27W91a-ofgCe9ur2m6bTghy77
&code_verifier=AdleUo9ZVcn0J7HkXOdzeqN6pWrW36K3JgVRwMW8BBQazEPV3kFnHyWIZi2jt'
Example Response
{
"access_token": "X81Pavwil2IhA75ayAK7XLObKHKVUr7vPbAMtCEnagpY9JLRyMqgd_6hquxjdUZ4",
"refresh_token": "SY5kZY6HPls2KWDM6jHhzYruQaNSmi_eS00PeftLgtsdHxPMlxsAbJ5WMN1MRGON",
"expires_in": 3600,
"token_type": "Bearer",
"scope": "email openid phone profile",
"id_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6IjlhYmM1N2ZmNGEwNzllNWY5NGQxZTUzZmRjYzZjZWZmMGNhNTM1Z
TUiLCJ0eXAiOiJKV1QifQ.eyJhdF9oYXNoIjoiY3lXUmxXcGlnT1VoNXJGRm5aY25ydyIsImF1ZCI6WyIzMmU1ZDEzYi0zMj
c3LTRmMDUtYTk3OC1hNmJiNzZlZTM3ZDkiXSwiYXV0aF90aW1lIjoxNTY1NjQ3ODk2LCJleHAiOjE1NjU2NTI1NTUsImdsb2
JhbF9zdWIiOiJjYXB0dXJlLXYxOi8vZGV2LWFwcC5qYW5yYWluY2FwdHVyZS5jb20vNnR1cWFodTlqN2Z1bXlla2ZnOXV4ZH
A1d3kvdXNlci9kODNiNGYwNS05N2FiLTQ1YjAtYjFlMC01MDcxZGQ1ODE2ZGQiLCJpYXQiOjE1NjU2NDg5NTUsImlzcyI6Im
h0dHBzOi8vdjEuYXBpLnVzLmphbnJhaW4uY29tLzAwMDAwMDAwLTAwMDAtMDAwMC0wMDAwLTAwMDAwMDAwMDAwMC9sb2dpbi
IsImp0aSI6IjdPS1Z0MkEybzl3bnlDaUtFZUFJUzk5TyIsIm5vbmNlIjoibjZuaWZod2FnOTkiLCJzdWIiOiJkODNiNGYwNS
05N2FiLTQ1YjAtYjFlMC01MDcxZGQ1ODE2ZGQifQ.FVtvQbHPrJGspbUW51vemB0rfgaHh7f2h6oooVhSPSSRhOd-gq68GnS
1XcrUJ97vvQUH6_mBpoBZFvKXYO0zJ_MT7H4fFcxe8RlEEUEbp_Wmjd1078IPwaa9xZ4LBeizKQ5EYALIMryASg2cy4Q7Bfs
heEbdvi43dEgYkOYe_5boUcfH32EWq86adM3cz8P_UdUMHWOpToFnkwQQeNWx5O9IFXJ-ITW4RGl2c6sZCrtL2RHpyK7KEav
HAzrKxtdvB5rVL25WDUJKyID7zsiH4VDhifvMH4qRJePa93491YOo50CLyqmkdHqU5DKsjb_rttcd5xxYkPeGvCqRgAzFbg"
}
Learn more about tokens by reading the article OpenID Connect Token Reference.
View/Update User Profile
After the user has an active session, provide a profile action element on your site/app (for example, a My Profile button). When the user clicks the action element, make a call to the /auth-ui/profile endpoint to display the Akamai-hosted profile page to the user.
Request Template
https://v1.api.<region>.janrain.com/<customer-id>/auth-ui/profile?client_id=<oidc-client-id>
Example Request
https://v1.api.us.janrain.com/12345678-1234-1234-1234-123456789012/auth-ui/profile?client_id=1ab23456-7c8d-90ef-g123-45hij6789012
Making the /auth-ui/profile call displays the Akamai-hosted profile page. For example:
Note that each of the three sections from the profile landing page can be called directly, if desired, by modifying the endpoint:
User Profile Section | Endpoint URL |
Personal Data | .../auth-ui/profile/data |
Account Security | .../auth-ui/profile/security |
Privacy Settings | .../auth-ui/profile/privacy |
Step 8: CNAMEs
CNAMEs
There are three Akamai Identity Cloud domains you can CNAME to match your company domain names. You must reach out to your Identity Cloud representative to start this process.
Domain | Default Value | Customization |
Hosted Login base URL This domain is used by all Hosted Login implementations. | https://v1.api.us.janrain.com | This domain be CNAMEd to the following subdomain (replacing mycompany with your real domain): https://accounts.mycompany.com |
Capture application Registration Domain This domain is used only if you are using social login. | https://mycompany.us.janraincapture.com | This domain appears in a message to the user after successful social authentication. For example: "Redirecting to https://mycompany.us.janraincapture.com/widget/token_url.” The Registration domain can be CNAMEd to the following subdomain: https://profiles.mycompany.com |
Engage application URL This domain is used only if you are using social login. | https://my-company.rpxnow.com | This domain might appear to the user within a social login identity provider’s webview, depending on the IdP. For example: "Sign in to my-company.rpxnow.com with your Yahoo ID.” The Engage application domain can be CNAMEd to the following subdomain: https://social.mycompany.com |