skip to Main Content

I’m new to AWS and just exploring possible architectures using the tools like AWS cognito, AWS Cloudfront, and/or AWS API Gateway.

Currently, my app is deployed in an EC2 instance and here is the outline:

Frontend: React app running on port 80. When a user goes to https://myapp.com, the request is be directed to my-ec2-instance:80.

Backend: Nodejs + Express running on port 3000. After the user loads the frontend in the browser, when he interacts with the website, http requests are sent to https://myapp.com/api/*, which are routed to my-ec2-instance:3000;

I use nginx/openresty as a single entry point to my webapp, and it does authorization with AWS Cognito, and then reverse-proxy the requests based on path:

enter image description here

Now, instead of managing an EC2 instance with the nginx/openresty service in it, I want to go serverless.

I plan to point my domain myapp.com to AWS CloudFront, and then Cloudfront acts as the single entry point to replace the functionalities of Nginx/Openresty. It should do the following:

  1. Authorization with AWS Cognito:
    When a user first visits myapp.com, he is directed to AWS Cognito from AWS Cloudfront to complete the sign-in step.

  2. path-based reverse proxy: I know this can be done. I can configure this from the CloudFront configuration page.

But for 1, Can Cloudfront do authorization with AWS Cognito? Is this the right way of using AWS Cloudfront?

After reading the AWS doc and trying with Cloudfront configurations, I started to think that Cloudfront is not build for such a use case at all.

Any suggestions?

3

Answers


  1. Few ideas.

    Frontend:
    Use S3 + CloudFront distribution.
    About the authentication, you can try using a Lambda function "linked" to the CloudFront distribution, redirecting to Cognito.

    Backend:
    Deploy on Fargate, EC2 or do you prefer.
    Put an Application Load Balancer (ALB) in front of the endpoint, so you can define rules with redirects, forward, deny, etc.

    Login or Signup to reply.
  2. You mentioned "serverless", but using ec2 which is a server. You can use AWS lambda (Node JS) for backend and S3 for front-end. AWS API gateway has built in authorization feature where you can use AWS Cognito. Cloudfront is for content delivery cached in edge locations to deliver content faster from nearest edge locations where the user is located.

    You can follow the below steps to implement serverless concept in AWS.

    1. Create the front end and upload to S3

    2. Configure AWS Cognito and grab the following
      UserPoolId: ‘xxxx’,
      ClientId: ‘xxxx’,
      IdentityPoolId: ‘xxxx’,
      Region: ‘xxxx’

    3. Use aws-cognito-sdk.min.js to authenticate user and get the JWT token, sample code can be found here. This JWT token needs to be passed to each and every API call in the header section. If using AJAX then sample code is

      var xhr = new XMLHttpRequest();

      xhr.setRequestHeader("Authorization", idToken);

    4. Configure AWS API gateway and cloudfront – follow documentation

    5. In API Gateway configuration select Cognito for those API’s for which you want to use authorized access.

    6. Create AWS Lambda functions for the backend and link to API Gateway.

    Login or Signup to reply.
  3. PROBLEMS

    It feels like your current problems are:

    • Requests to Cloudfront will require a cookie, and Cloudfront has only very limited capabilities for running code to verify them (via lambda edge extensions)
    • It does not make sense to put a reverse proxy in front of Cloudfront, since it should deploy web resources to 20 or so global locations for you

    SOLUTION APPROACH

    If you can separate web and API concerns you can solve your problem:

    • Make your Express web back end (used during local development) serve only static content
    • Use the reverse proxy and cookies only for API and OAuth requests

    TOKEN HANDLER PATTERN

    At Curity we have put together some related resources, illustrated in the following picture:

    Token Handler Pattern

    It is a tricky flow from a deployment viewpoint, though the idea is to just plug in the token handler components, so that your SPA and APIs require only simple code, while also using the best security.

    AWS CODE EXAMPLE

    Out of interest a React sample of mine uses this pattern with Cognito, and is deployed to Cloudfront.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search