I've been building a serverless REST API with AWS API Gateway, Lambda and the Serverless Framework. I want to build a website on which users sign up, choose an API plan (free, basic, pro) and get the corresponding long-lived API Key with which they can query the serverless API a certain number of times a month.
I understand that with Cognito and the self-hosted UI, you can handle user authentication easily with CUP (Cognito User Pool) Tokens, which are actually Json Web Tokens. I would like to automatically create and associate an API Key to a Usage Plan, and then to the Cognito User.
The first part is easy: with the AWS Javascript SDK, it's as simple as doing:
var params = {
keyId: 'whateverKeyId', /* required */
keyType: 'API_KEY', /* required */
usagePlanId: 'whateverUsagePlanId' /* required */
};
apigateway.createUsagePlanKey(params, function(err, data) {
if (err) console.log(err, err.stack); // an error occurred
else console.log(data); // successful response
});
I'm struggling with the second part... Should I add the API Key as a custom attribute to the User Pool? But then, I don't really know how to retrieve the API Key. The documentation isn't really clear. Add the user and API Key to my own DynamoDB database after sign-up (which would be a waste of Cognito really)?
To be honest, this looks like a common scenario and the fact that I spent three days looking for the solution all over the internet without success makes me think that there's something that I don't understand...
Thanks in advance for your input!
As an alternative to using IAM roles and policies or Lambda authorizers (formerly known as custom authorizers), you can use an Amazon Cognito user pool to control who can access your API in Amazon API Gateway.
API keys are alphanumeric strings that are distributed to developers to grant access to an API. API Gateway can generate these on your behalf, or you can import them. Usage plans let you provide API keys to your customers so that you can track and limit their usage.
It is a good choice to add the API key as a custom attribute in Cognito user pool.
Every time that your user signin, cognito returns an ID token in JWT format. From this token you can retrieve cognito user's attributes both the custom attr and the default. You can find further details for cognito tokens here:
https://docs.aws.amazon.com/cognito/latest/developerguide/amazon-cognito-user-pools-using-tokens-with-identity-providers.html
and
https://aws.amazon.com/premiumsupport/knowledge-center/decode-verify-cognito-json-token/
So what you can do:
If you do the above steps, then this JWT token will be passed to your Lambda function and inside lambda function you can retrieve the cognito custom attribute (API Key):
const API_ID = event.requestContext.authorizer.claims['custom:apiid'];
The above line, retrieves the JWT from your API authorizer header, and then retrieves the custom attribute that you created in cognito, which called "apiid" or however you want to name it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With