Seanimus
Seanimus

Reputation: 567

SAM Template - API Authorizor to use existing Cognito User Pool

UPDATE: Thanks for the help!

I've updated the template.yml to include the Authorizer, but I'm getting an error still:

  HelloWorldApi:
    Type: AWS::Serverless::Api
    Properties:
      StageName: Prod
      Cors: "'*'"
      # Auth:
      #   DefaultAuthorizer: MyCognitoAuthorizer
      #   Authorizers:
      #     MyCognitoAuthorizer:
      #       UserPoolArn: arn:aws:cognito-idp:us-east-1:719235216593:userpool/my-user-pool-id



  HelloWorldFunction:
    Properties:
      CodeUri: hello-world/
      Handler: app.lambdaHandler
      Runtime: nodejs10.x
      Events:
        HelloWorld:
          Type: Api 
          Properties:
            RestApiId: !Ref HelloWorldApi
            Path: /hello
            Method: get

  MyCognitoAuthorizer: 
    Type: AWS::ApiGateway::Authorizer
    Properties:
      Name: MyAuthorizer
      Type: COGNITO_USER_POOLS
      RestApiId: !Ref HelloWorldApi
      ProviderARNs:
        - arn:aws:cognito-idp:us-east-1:719235216593:userpool/my-user-pool-id

However, I'm now getting the following when trying to create the stack:

The following resource(s) failed to create: [MyCognitoAuthorizer, HelloWorldApiDeploymentbc8438953d, HelloWorldFunctionHelloWorldPermissionProd]. . Rollback requested by user.

I did not specify the rollback, and I can't determine what is wrong in my authorizer?


ORIGINAL

I have built multiple lambdas, each having their own Api Gateway. I'm using SAM CLI to do this, and each lambda is its own project and has it's own Template.yml file describing the infrastructure.

Below is an example templay.yml:

AWSTemplateFormatVersion: '2011-09-09'
Transform: AWS::Serverless-2016-10-31

Resources:
    # Avoid 'implicit API' creation via SAM by explicitly defining one
    HelloWorldApi:
        Type: AWS::Serverless::Api
        Properties:
          StageName: Prod
          Cors: "'*'"


    HelloWorldFunction:
        Type: AWS::Serverless::Function 
        Properties:
          CodeUri: hello-world/
          Handler: app.lambdaHandler
          Runtime: nodejs10.x
          Events:
            HelloWorld:
              Type: Api 
              Properties:
                RestApiId: !Ref HelloWorldApi # reference defined API
                Path: /hello
                Method: get

I would now like to provide authentication for each lambda. However, I would like all the lambdas to use the same Cognito User pool. I've seen many examples that create the associated userpool with the lambda, but in this case I would end up with a new userpool for every lambda.

Is there a way I can specify within the template.yml the ARN of an existing userpool I created via the AWS console?

Note: I'm not very familiar with CloudFormation syntax, so it's preferable if this is doable with the SAM CLI template syntax.l

Upvotes: 3

Views: 3304

Answers (2)

Dave Baghdanov
Dave Baghdanov

Reputation: 2358

You should be able to specify the Authorizer in the API template:

  HelloWorldApi:
    Type: AWS::Serverless::Api
    Properties:
      StageName: Prod
      Cors: "'*'"
      Auth:
        DefaultAuthorizer: MyCognitoAuthorizer
        Authorizers:
          MyCognitoAuthorizer:
            UserPoolArn: !Ref MyCognitoUserPoolArn

  HelloWorldFunction:
    Properties:
      CodeUri: hello-world/
      Handler: app.lambdaHandler
      Runtime: nodejs10.x
      Events:
        HelloWorld:
          Type: Api 
          Properties:
            RestApiId: !Ref HelloWorldApi
            Path: /hello
            Method: get

Have you looked at this sample?

https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/serverless-controlling-access-to-apis.html#serverless-controlling-access-to-apis-cognito-user-pool

Upvotes: 0

Pat Myron
Pat Myron

Reputation: 4648

Existing resources created outside of CloudFormation can be referenced in templates by simply hardcoding the desired identifier (ARNs in this case):

    Authorizer:
      Type: AWS::ApiGateway::Authorizer
      Properties:
        Type: COGNITO_USER_POOLS
        RestApiId: !Ref HelloWorldApi
        ProviderARNs:
          - # hardcoded Cognito User Pool ARN

AWS::ApiGateway::Authorizer documentation

Cognito User Pool ARN format


You should be able to find your Cognito User Pool's ARN on Cognito's console

Upvotes: 4

Related Questions