AppleBaggins
AppleBaggins

Reputation: 454

CognitoIdentityCredentials not providing access

I'm not sure if I'm understanding the process correctly, but I'm using a Cognito User Pool and authenticating. I receive my tokens as expected. I'm trying to call CognitoIdentityCredentials according the documentation as part of my onSuccess authentication flow.

AWS.config.update({
    credentials: new AWS.CognitoIdentityCredentials({
        IdentityPoolId: IdentityPoolId,
    }),
    region: 'us-east-1'
});

I have IAM roles assigned to my Cognito Identity Pool and everything looks like it's configured correctly. However, I don't receive any AWS credentials.

The documentation states:

By default this provider gets credentials using the AWS.CognitoIdentity.getCredentialsForIdentity() service operation, which requires either an IdentityId or an IdentityPoolId (Amazon Cognito Identity Pool ID), which is used to call AWS.CognitoIdentity.getId() to obtain an IdentityId.

Do I need to call AWS.CognitoIdentity.getId() manually to get AWS credentials?

Upvotes: 3

Views: 5672

Answers (3)

William Trevena
William Trevena

Reputation: 276

Using the aws-sdk for JavaScript v3, I was finally able to get a Cognito User's Credentials & IdentityId from a Cognito User's identity jwtToken using the following code in a JavaScript Lambda Function invoked via API-Gateway with a Cognito User Pool Authorizer (the jwtToken is passed into the Authorization header of the request):

const IDENTITY_POOL_ID = "us-west-2:7y812k8a-1w26-8dk4-84iw-2kdi849sku72"
const USER_POOL_ID = "cognito-idp.us-west-2.amazonaws.com/us-west-2_an976DxVk"
const { CognitoIdentityClient } = require("@aws-sdk/client-cognito-identity");
const { fromCognitoIdentityPool } = require("@aws-sdk/credential-provider-cognito-identity");

exports.handler = async (event,context) => {
        const cognitoidentity = new CognitoIdentityClient({
            credentials:  fromCognitoIdentityPool({
                client: new CognitoIdentityClient(),
                identityPoolId: IDENTITY_POOL_ID,
                  logins: {
                      [USER_POOL_ID]:event.headers.Authorization
                  }
            }),
        });

        var credentials = await cognitoidentity.config.credentials()
        console.log(credentials)
        // {
        //    identityId: 'us-west-2:d393294b-ff23-43t6-d8s5-59876321457d',
        //    accessKeyId: 'ALALA2RZ7KTS7STD3VXLM',
        //    secretAccessKey: '/AldkSdt67saAddb6vddRIrs32adQCAo99XM6',
        //    sessionToken: 'IQoJb3JpZ2luX2VjEJj//////////...', // sessionToken cut for brevity 
        //    expiration: 2022-07-17T08:58:10.000Z
        //  }

        var identity_ID =  credentials.identityId
        console.log(identity_ID)

        const response = {
            statusCode: 200,
            headers: {
                "Access-Control-Allow-Headers": "*",
                "Access-Control-Allow-Origin": "*",
                "Access-Control-Allow-Methods" : "OPTIONS,POST,GET,PUT"
            }, 
            body:JSON.stringify(identity_ID)
        };
        return response;
}

After a Cognito User has signed in I can use the Auth directive of aws-amplify directive and fetch() in my React-Native app to invoke the lambda function shown above by sending a request to my API-Gateway trigger (authenticated with a Cognito User Pool Authorizer) by calling the following code:

import { Auth } from 'aws-amplify';
var APIGatewayEndpointURL = 'https://5lstgsolr2.execute-api.us-west-2.amazonaws.com/default/-'
var response = {}

async function getIdentityId () {
       
   var session = await Auth.currentSession()
   var IdToken = await session.getIdToken()
   var jwtToken = await IdToken.getJwtToken()

   var payload = {}
       
   await fetch(APIGatewayEndpointURL, {method:"POST", body:JSON.stringify(payload), headers:{Authorization:jwtToken}})
       .then(async(result) => {
             response = await result.json()
             console.log(response)
        })
}

More info on how to Authenticate using aws-amplify can be found here https://docs.amplify.aws/ui/auth/authenticator/q/framework/react-native/#using-withauthenticator-hoc

Upvotes: 5

lemming
lemming

Reputation: 1863

No, AWS.CognitoIdentityCredentials() calls getId().

You simply need to provide the id_token received after authentication from your Cognito User Pool in the Logins map of the params for AWS.CognitoIdentityCredentials(), as shown in "Accessing AWS Resources Using an Identity Pool".

// Add the User's Id Token to the Cognito credentials login map.
AWS.config.credentials = new AWS.CognitoIdentityCredentials({
    IdentityPoolId: 'YOUR_IDENTITY_POOL_ID',
    Logins: {
        'cognito-idp.<region>.amazonaws.com/<YOUR_USER_POOL_ID>': 'YOUR ID_TOKEN RETURNED FROM AUTHENTICATION WITH COGNITO USER POOLS'
    }
}, { region: 'us-east-1'});

Upvotes: 4

senaykt
senaykt

Reputation: 68

If you're using authenticated identity pool, you should get AWS Credentials with id_token.

Upvotes: 0

Related Questions