9
votes

I have a question about the integration of Cognito and API Gateway and I hope that you can help me with that. I am thinking of making an application in which I would like the authentication process with third parties (Facebook, Twitter ...), so I discard Cognito User Pool, then I have Cognito Identity Pool, but this is where my doubts grow.

  • How can I integrate it with API Gateway?
  • Should I use API Gateway Custom Authorizer to manage the token generated by Cognito?
  • If I do not use the Custom Authorizer, How can I restrict access to the API Methods based on the user profile (admin, client ...)?

Thanks for your help

2

2 Answers

7
votes

How can I integrate it with API Gateway?

  • For Cognito Identity Pools, you'll set the Authorization type on your methods to AWS_IAM

Should I use API Gateway Custom Authorizer to manage the token generated by Cognito?

  • With Identity Pools, this won't be possible. You'll have to use the AWS_IAM authorization. You'll get access to the Cognito ID for your backend call.

If I do not use the Custom Authorizer, How can I restrict access to the API Methods based on the user profile (admin, client ...)?

  • Someone more familiar Cognito would be able to answer better, but I believe you can only set up the 'authenticated role' and the 'unauthenticated role'. So when a user authenticates with an external provider, they get the 'authenticated role' and that's it. I'm not sure if there is support for user groups (admin, client) in Identity Pools (there is support in User Pools).

Edit: maybe this will help http://www.slideshare.net/AmazonWebServices/securing-serverless-workloads-with-cognito-and-api-gateway-part-i-aws-security-day

0
votes

You can use the aws-sdk to generate a signed request to API Gateway if authorizer is set as AWS_IAM. First get some temporary credentials, then create a signed request.

Get Credentials (example with javascript sdk ) :

var AWS = require('aws-sdk')

var cognitoidentity = new AWS.CognitoIdentity();

var makeSignedRequest = async function () {
    var params = {
      IdentityId: 'STRING_VALUE', /* required */
      CustomRoleArn: 'STRING_VALUE',
      Logins: {
        '<IdentityProviderName>': 'STRING_VALUE',
        /* '<IdentityProviderName>': ... */
      }
    };
    var credsForIdentity = await cognitoidentity.getCredentialsForIdentity(params).promise()
    var httpRequest = new AWS.HttpRequest("https://<API_GATE_WAY_ENDPOINT", "<region>");
    httpRequest.headers.host = "<API_GATE_WAY_ENDPOINT>"; // Do not specify http or https!!

    AWS.config.credentials = {
        accessKeyId: creds.Credentials.AccessKeyId,
        secretAccessKey: creds.Credentials.SecretKey,
        sessionToken: creds.Credentials.SessionToken
    }
    httpRequest.method = "POST";
    httpRequest.body = JSON.stringify(data)

    var v4signer = new AWS.Signers.V4(httpRequest, "execute-api");
    v4signer.addAuthorization(AWS.config.credentials, AWS.util.date.getDate());

    const rawResponse = await fetch(httpRequest.endpoint.href , {
        method: httpRequest.method,
        headers: httpRequest.headers,
        body: httpRequest.body
    });


}

This example is not perfect but it is a good starting point on signed request in AWS.

Of course, don't forget to give proper permissions to your authenticated identities so that they can invoke the API.