- Newest
- Most votes
- Most comments
Yes, it is possible to simplify your authentication process and access tenant information in the Pre-Token Generation Lambda function without relying on a three-step process or using the custom:CurrentTenant attribute. You can achieve this by leveraging Amazon Cognito's clientMetadata parameter and modifying your authentication flow.
Here's how you can implement this:
-
When redirecting users to the Cognito Managed Login Page, include the tenant information in the clientMetadata parameter. This parameter allows you to pass custom key-value pairs to your Lambda function.
-
In your Pre-Token Generation Lambda function, you can access the clientMetadata information directly. This allows you to retrieve the tenant information without needing to store it in a custom attribute or perform additional steps.
-
Use the tenant information within your Lambda function to fetch the necessary user claims from the appropriate tenant database and add them to the ID token.
-
Configure your user pool to send a version 2 event to the Lambda function, which allows for access token customization in addition to ID token customization.
By implementing this approach, you can reduce the authentication process to a single step, obtaining the token (including claims) directly with response_type=token. This eliminates the need for the additional steps of exchanging the code for a token and refreshing the token after setting the custom attribute.
This method not only simplifies your authentication flow but also improves performance by reducing the number of API calls and eliminating the need for token refreshing. It allows you to maintain your multi-tenant architecture while streamlining the authentication process for a better user experience.
Remember to ensure that your Lambda function is properly secured and that you handle the clientMetadata securely, as it will contain sensitive tenant information. Also, make sure to update your frontend application to include the necessary clientMetadata when initiating the authentication process.
Sources
Pre token generation Lambda trigger - Amazon Cognito
Community | Cognito Starter Kit with Rust and Lambda
How authentication works with Amazon Cognito - Amazon Cognito
Hi,
To investigate why the ClientMetadata is empty, we require account and resource details that are non-public information. Please open a support case with AWS using the following link.
To bypass the extra step of exchanging the authorization code for tokens at the /token endpoint, you can make use of the Implicit grant (response_type=token) by enabling this grant on your app client. This is however a legacy grant and is not recommended as tokens are exposed in the callback fragment.
As you correctly mentioned, Lambda triggers cannot access the state parameter. Considering that ClientMetadata is sent to the Lambda function using either the AdminRespondToAuthChallenge or RespondToAuthChallenge APIs which can be seen in the documentation, I suspect that this is the reason ClientMetadata is empty as you are using the /login endpoint to authenticate and not the user pool APIs InitiateAuth and RespondToAuthChallenge.
clientMetadata
To pass this data to your Lambda function, use the ClientMetadata parameter in the AdminRespondToAuthChallenge and RespondToAuthChallenge API operations. Amazon Cognito doesn't include data from the ClientMetadata parameter in AdminInitiateAuth and InitiateAuth API operations in the request that it passes to the pre token generation function.
Relevant content
- asked 2 years ago

I've already tried ClientMetadata. It does not work. For more information; I am redirecting user to Cognito Managed Login Page as below; https://.amazoncognito.com/login?client_id=&prompt=login&redirect_uri=***&response_type=code&scope=openid+profile+aws.cognito.signin.user.admin&state=tenant%3Dadmin
In PreTokenGenerator Lambda I've logged the Client Metadata as below. It is empty;
public async Task<CognitoPreTokenGenerationEvent> idsPreTokenGenerationHandler(CognitoPreTokenGenerationEvent cognitoEvent, ILambdaContext context) {
foreach (var item in cognitoEvent.Request.UserAttributes) { context.Logger.LogLine($"UserAttributes:Key: {item.Key}, Value: {item.Value}"); }
}