Skip to content

Instantly share code, notes, and snippets.

@stevekinney
Last active September 9, 2023 18:55
Show Gist options
  • Star 99 You must be signed in to star a gist
  • Fork 43 You must be signed in to fork a gist
  • Save stevekinney/6ab02582829f039b6a14c973923909f8 to your computer and use it in GitHub Desktop.
Save stevekinney/6ab02582829f039b6a14c973923909f8 to your computer and use it in GitHub Desktop.

Frontend Masters: AWS for Frontend Engineers

You should have the following completed on your computer before the workshop:

  • Install the AWS CLI.
  • Have Node.js installed on your system. (Recommended: Use nvm.)
    • Install yarn with brew install yarn.
  • Create an AWS account. (This will require a valid credit card.)
  • Create a Travis CI account. (This should be as simple as logging in via GitHub).

Follow-Along Guides: I made a set of visual follow-along guides that you can reference throughout the course.

Repositories

  • Noted (Base): This is the base that you can clone and work with.
  • Noted (Live): This is the live version that I'm going to be working with.

Useful Links

S3 Bucket Policy

This might be helpful at some point.

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": "*",
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::YOUR_BUCKET_NAME_HERE/*"
        }
    ]
}

Travis Configuration

language: node_js
node_js:
  - '8'
cache:
  yarn: true
  directories:
    - node_modules
script:
  - yarn test
before_deploy:
  - yarn global add travis-ci-cloudfront-invalidation
  - yarn run build
deploy:
  provider: s3
  access_key_id: $AWS_ACCESS_KEY_ID
  secret_access_key: $AWS_SECRET_ACCESS_KEY
  bucket: $S3_BUCKET
  skip_cleanup: true
  local-dir: dist
  on:
    branch: master
after_deploy:
  - travis-ci-cloudfront-invalidation -a $AWS_ACCESS_KEY_ID -s $AWS_SECRET_ACCESS_KEY -c $CLOUDFRONT_ID -i '/*' -b $TRAVIS_BRANCH -p $TRAVIS_PULL_REQUEST

Redirecting to index.html on Valid Client-side Routes

Viewer Request

exports.handler = (event, context, callback) => {
  const request = event.Records[0].cf.request;

  console.log('Before', request.uri);

  if (/notes\/\d(\/edit)?/.test(request.uri)) {
    request.uri = '/index.html'
  }

  console.log('After', request.uri);

  callback(null, request);
};

Implementing Security Headers

Viewer Response

'use strict';

exports.handler = (event, context, callback) => {
  const response = event.Records[0].cf.response;

  response.headers['strict-transport-security'] = [{
    key: 'Strict-Transport-Security',
    value: 'max-age=31536000; includeSubDomains'
  }];

  response.headers['content-security-policy'] = [{
    key: 'Content-Security-Policy',
    value: "default-src 'self'"
  }];

  response.headers['x-xss-protection'] = [{
    key: 'X-XSS-Protection',
    value: '1; mode=block'
  }];

  response.headers['x-content-type-options'] = [{
    key: 'X-Content-Type-Options',
    value: 'nosniff'
  }];

  response.headers['x-frame-options'] = [{
    key: 'X-Frame-Options',
    value: 'DENY'
  }];

  callback(null, response);
};

Implementing a Redirect

Origin Request

exports.handler = (event, context, callback) => {
  const request = event.Records[0].cf.request;

  const response = {
    status: '302',
    statusDescription: 'Found',
    headers: {
      location: [{
        key: 'Location',
        value: 'https://bit.ly/very-secret'
      }],
    },
  };

  if (request.uri === '/secret') {
    console.log('Got it');
    return callback(null, response);
  }

  console.log('Nope');
  callback(null, request);
};
@laniehei
Copy link

Users on Windows: when downloading the AWS CLI, ensure that you are scrolling down in the documentation, and following the specific "for Windows" installation guide so that you don't have a bad time.

@Whatapalaver
Copy link

Whatapalaver commented Jun 9, 2019

TRAVIS CONFIGURATION COMMENT
I seem to have been unable to force AWS to use the us_east-1 region
If you are in a similar boat it's worth noting that travis ci assumes this region and builds will fail as a result.
It's an easy fix, just add the region into the deploy section of the travis.yml or use another ENV variable.
For me this looks like:
region: eu-west-2

@Miteshdv
Copy link

Miteshdv commented Dec 4, 2020

It Seems AWS has made this complete solution easy , by using Cloud Formation and AWS Static Site Storage

https://github.com/aws-samples/amazon-cloudfront-secure-static-site#user-content-amazon-cloudfront-secure-static-website

Please Confirm if this solution is as good as yours explained in Course

@stevekinney
Copy link
Author

They both accomplish the same thing. So, whatever is more appealing to you should work.

@krfong916
Copy link

krfong916 commented Feb 22, 2021

Hi Steve, how would you set CSP headers for this configuration (caching a static SPA), while using a 3rd party component library? Given that inline styles will be injected to the document at runtime and not at build time, from your view, how would one handle this? What would a meta tag look like?

I would most like to hear your thoughts. Thank you.

@JLowe-N
Copy link

JLowe-N commented Apr 7, 2022

I've got everything working except for the rickroll redirect from Origin Request.
I can see the 302/301 passthrough from Origin Request, but I can't seem to get the Location header to passthrough to bit.ly/very-secret.
It works if I change that header on Viewer Response (along with the security headers we did in a previous step).

This example seems to match AWS' example of Origin Request, with the only difference being that it is the same-origin domain relative route versus the absolute route to https://bit.ly/very-secret.

Just noticed V2 was also released, seems the obvious new things was the Cloudfront Functions and OAI (Cloudfront Only Access to S3).

Thanks for hosting these courses!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment