Integrate a single-page app
This is part two of a four-part article, Integrate with Identity Cloud hosted pages.
Overview
Who is this article for?
This is part two of a step-by-step guide for developers that wish to use ForgeRock SDK with Hosted Pages. The goal is to give you practical advice about themes and provide some best practices along the way.
Prior knowledge configuring Identity Cloud is helpful but not assumed.
What is a single-page app?
A single-page app (SPA) is an app that runs inside a browser and does not require page reloading during use. You use this type of app every day. For example: Gmail, Google Maps, Facebook, and GitHub.
An SPA is all about providing an outstanding user experience by imitating a "natural" environment in the browser—no page reloads, no extra wait time. An SPA lets you visit just one web page which uses JavaScript to load all content that requires JavaScript.
An SPA requests the markup and data independently, rendering pages straight in the browser. SPAs frequently use popular JavaScript frameworks like AngularJS, Vue.js, React, and more.
The ForgeRock JavaScript SDK
ForgeRock provides the ForgeRock JavaScript SDK. Use the SDK to integrate your SPAs with the Identity Cloud.
The ForgeRock JavaScript SDK allows you to rapidly build JavaScript apps against the ForgeRock REST APIs.
The SDK supports:
-
Registration and Authentication Trees
-
Access Token Acquisition
-
Session Handling
Integrate a single-page app with Identity Cloud
Build the UI
Using the framework of your choice, create a new app. You will configure the app to authenticate using Identity Cloud.
When building your SPA, you have two options for integrating with ForgeRock:
Option 1: Integrate via APIs and build your own UI.
Option 2: Use the Hosted Pages in your app (Centralized UI).
The SDK supports both options, allowing you to tailor your experience to your needs. Choose the Option that best meets your project and use case requirements.
A custom UI vs a centralized UI
Building a custom UI for your SPA allows you to have full control of the user experience, the branding, and the theme of your app. A custom UI allows you full customization control, but requires more development effort. Each app that uses the platform must build its own UI.
This might be problematic for projects where various SPAs point to a central authentication point to gain authentication privileges. In this case, if the UI/UX requirements allow it, we recommend using a Centralized UI.
What is a centralized UI
The ForgeRock SDKs let you configure multiple apps on multiple platforms. You can reuse the user interface from ForgeRock® Access Management (AM) or your own web app. You do not have to manage authentication yourself.
As the UI is centralized in the cloud, changes you make to an authentication journey in AM are available to all apps that use the UI. You do not need to rebuild or redeploy the apps.
Since your app does not manage authentication journeys, it does not need access to user credentials. This reduces complexity and risk.
The ForgeRock SDK manages and stores tokens - providing a seamless single sign-on experience.
Additionally, apps that use a centralized UI are not affected by the new third party cookie restrictions being rolled out in modern web browsers.
To learn more about centralized UI, visit Use centralized login.
Configure Identity Cloud
Before you begin, follow the instructions in one of the following sections:
In the following example, you configure:
- In Identity Cloud
-
-
OAuth2.0 provider
-
OAuth2.0 client
-
- In the client applications
-
-
JS
-
Configure the OAuth2.0 provider
-
In the Platform Admin UI, log in to the AM Native console.
-
In the AM Native console, click Services.
-
If there is no OAuth2 Provider, create one using the default settings.
-
In the OAuth2 Provider configuration, on the Consent tab, enable the Allow Clients to Skip Consent option.
-
On the Configure OAuth2 tab, enable the Issue Refresh Tokens option.
-
On the Advanced OpenID Connect tab, enable the claims_parameter_supported option.
Configure the OAuth2.0 client
-
In the AM Native console, navigate to Applications > OAuth 2.0 > Clients.
-
Create a new OAuth 2.0 client named “sdkPublicClient”.
-
Set the following properties:
-
Client ID = sdkPublicClient
-
Client secret = (leave blank)
-
Redirection URIs = https://localhost:8443
-
Scope(s) = openid profile email address
-
-
Click Create.
-
On the Core tab:
-
Set the Client type property to Public.
-
Disable the Allow wildcard ports in redirect URIs property.
-
-
Click Save.
-
On the Advanced tab:
-
In the Grant Types field, ensure that the Authorization Code value is present.
-
Set the Token Endpoint Authentication Method field to None.
-
Enable the Implied consent property.
To properly enable implied consent, the OAuth2 Provider must be configured to allow clients to skip consent. For more information, see the AM reference documentation.
-
-
Click Save.
Configure your app to use centralized UI
In this example, you use a centralized UI to authenticate your app.
You configure the app to use the Identity Cloud authentication hosted page you used in part one of this tutorial.
To learn more about centralized UI, visit Use centralized login. |
Let’s see how you can do that in more detail:
For this example, you are going to import the ForgeRock SDK using the NPM package, assuming you are using a CommonJS Bundler.
A CDN proxy and other approaches are available.
const forgerock = require('@forgerock/javascript-sdk'); |
-
Create a centralized login instance using the
Config
class. -
There is a close relationship between your app configuration and your OAuth 2.0 client configuration. Make sure they match.
forgerock.Config.set({ serverConfig: { baseUrl: 'https://openam-forgerock-sdks.forgeblocks.com/am', timeout: 90000 }, realmPath: 'alpha', clientId: 'sdkPublicClient', redirectUri: 'https://localhost:8443', // Example: the alias from the prerequisites section scope: 'openid profile email address', });
-
Create a login button with the tag ‘#loginBtn’.
-
Initiate authentication using the centralized UI feature.
document.querySelector('#loginBtn').addEventListener('click', () => { /** * The key-value of `login: redirect` is what allows central-login. * @note async await could be used in place of promises for greater clarity */ forgerock .TokenManager .getTokens({ login: 'redirect' }) .then(() => {forgerock .UserManager .getCurrentUser() .then((user) => showUser(user)); }); });
-
Create a way to logout.
document.querySelector('#logoutBtn').addEventListener('click', () => { try { Forgerock .FRUser .logout() .then(() => location.assign(`${document.location.origin}`)) } catch (error) { console.error(error); } });