Skip to main content

Accessing a connection's API via access tokens

Authress provides login aggregation, and it makes federated login easier. It does this by creating optimized user access tokens to be used and verified by service APIs. Authress creates access tokens specifically for your application.

During the login process, the third party provider configured as an Authress OAuth Connection, can save the login credentials in a credential vault. This vault enables your user in your app's UI or through an app's API to connect to the third party using the credential saved in the vault.

Credential Vaultsโ€‹

Authress is able to connect with any registered OAuth provider. The result of the login with the third party provider is a credential saved in the Authress Credential Vault.

When an access token is requested from the connection's credential vault, Authress determines if the current available token will still be valid for a sufficient length of time, and if not will automatically refresh it to generate a new access token. It does this using the OAuth configuration in the connection, and without ever revealing the refresh token at any time.

Refreshing the access token after it expires is part of OAuth, and every OAuth provider configured in Authress supports this. However, some of them need to be explicitly configured using the OAuth Refresh or Offline access configuration.

Setupโ€‹

The critical step is to configure the federated login provider to make sure it also returns a long lived refresh token. This is usually done via the connectionProperties on authentication. For the Google OAuth connection provider, refresh tokens are generated when the access_type property is configured to be offline.

(Note: This is the configuration for the Google connection, other OAuth connections may use a different and non-standard configuration to enable this functionality. Make sure to review the connection provider's documentation before configuring the connection).

Additionally, an identity provider may not always return the necessary refresh token or the right scopes, in these cases, be sure to follow closely the relevant login OAuth client setup and use the following connectionProperties as strictly documented. For the Google oauth client, you would use the following:

Request user offline access to Google
import { LoginClient } from '@authress/login';

const loginClient = new LoginClient({
authressLoginHostUrl: 'https://auth.yourdomain.com',
applicationId: 'Application_ID' });

await loginClient.authenticate({ connectionId: 'google',
// For Google login, offline access is configured via `access_type` property
// https://developers.google.com/identity/protocols/oauth2/web-server#offline
connectionProperties: {
scope: 'email openid profile additional_google_scope',
access_type: 'offline',
// Refresh token still missing, add this line:
prompt: 'select_account consent'
}
});

Client side accessโ€‹

After a user logs in with their selected OAuth identity provider and is redirected through Authress back to your application UI, there is an opportunity to exchange the Authress JWT for the provider credential. If the UI decides to interact with the provider's API directly in the browser, the Authress Login SDK can be used to fetch the provider access token:

(Application UI) Get a user's third party access token
import { loginClient } from '@authress/login';

async function makeProviderApiCall() {
const credentials = await loginClient.getConnectionCredentials();
const accessToken = credentials.accessToken;
const result = await fetch('https://api.provider.com/v1/api/path',
{ method: 'GET', headers: { 'Authorization': `Bearer ${accessToken}` } });
return result;
}

Service side accessโ€‹

Alternatively, requests may want to be made async from the service side, even when the user isn't logged in. There may be relevant background tasks that need to be performed, or long running actions. (Here are examples of long running transaction architecture in case one of those patterns better matches the use case).

In this circumstance, the context is the service client. Since the credentials are saved in the Authress connection vault, create and grant a service client the Authress role: UserCredentialsViewer to Authress:Connections/*/Users/*/Credentials, and then the service client can access the credentials for the user.

Generate a Service Clientโ€‹

You'll need a long lived service client to access the Authress API. Start by creating the Authress Service Client, by navigating to the Management Portal and clicking Add client.

Next you'll need to assign permissions and generate the secret access key.

Assign permissionsโ€‹

While editing the service client, navigate to the service client permissions section of the configuration, and click Assign client permissions. This will redirect you to the Service Client specific Access Record, enabling you the ability to give the new client permissions to use the Credential Vault for the relevant connection.

Grant permissions

And then create the access record with the Connection Credentials permission:

  • Authress:Connections/*/Users/*/Credentials

Connection credential vault permission

Generate the access keyโ€‹

By clicking Add key you generate a long lived access key. This access key will only be displayed on the screen one time to ensure the key remains secure:

generate the access key

Use the Access Key to get the credentialsโ€‹

(Service) Get a user's third party access token
import { AuthressClient } from '@authress/sdk';

async function makeProviderApiCall() {
// Your authress custom domain, found: https://authress.io/app/#/api?route=overview
const host = 'https://auth.yourdomain.com';

// Your service client secret can be obtained by navigating to https://authress.io/app/#/settings?focus=clients
// * Edit the Service Client, scroll to Manage secret access keys, and click `Add key`
const serviceClientSecretAccessKey = 'sc_aaa.acc_001.secret';
const authressClient = new AuthressClient({ authressApiUrl: host }, serviceClientSecretAccessKey);

// The user's Authress user ID
const userId = 'u_a001';
// The provider's OAuth connection registered in Authress
const connectionId = 'con-AAyzR1';

const response = await authressClient.connections.getConnectionCredentials(connectionId, userId);
const accessToken = response.data.accessToken;

// Make the API call to the third party's API:
const result = await fetch('https://api.provider.com/v1/api/path',
{ method: 'GET', headers: { 'Authorization': `Bearer ${accessToken}` } });
return result;
}

Additional resourcesโ€‹

Take a look at the full API documentation to see what else is possible.