Skip to main content

Other Ways to Deploy

We don't want to worry about potentially changing infrastructure just to deploy content changes to the site, so it's good to know other (and typically faster) ways to deploy besides running cdk deploy.

All of these approaches use the AWS CLI.

AWS CLI in the Terminal

This only takes three commands:

  1. Build the site (from the top-level folder, not aws-infra):

    npm run build
  2. Sync the local build to the S3 bucket (upload new/changed files, delete files that no longer exist):

    aws s3 sync ./build s3://your-s3-bucket-name --delete

    Replace your-s3-bucket-name with your S3 bucket name, which can be found in the AWS console.

  3. Clear the CDN cache so it serves the latest files:

    aws cloudfront create-invalidation --paths "/*" --distribution-id YOUR_CDN_ID

    Replace YOUR-CDN-ID with your CloudFront distribution ID, which can be found in the AWS console.

npm run script

Who wants to type those AWS commands all the time? Since we are already using npm and package.json files, let's setup the aws commands as npm run scripts.

Open up package.json (the top-level one, not the one in aws-infra) and add to the "scripts":

package.json
"scripts": {
"docusaurus": "docusaurus",
"start": "docusaurus start",
...
"typecheck": "tsc",
"s3-sync": "aws s3 sync ./build s3://your-s3-bucket-name --delete",
"cdn-sync": "aws cloudfront create-invalidation --paths '/*' --distribution-id YOUR_CDN_ID",
"deploy": "npm run build && npm run s3-sync && npm run cdn-sync"
},
warning

Docusaurus already defines a deploy script:

package.json
"deploy": "docusaurus deploy",

Docusaurus's deploy isn't compatible with our AWS infrastructure, so delete that and replace it with the new deploy script that uses the AWS CLI.

Now you can run:

npm run deploy

Github Action

If you're using github.com for version control, you can automatically trigger the deploy whenever you push/merge code to your main branch, by adding the file .github/workflows/deploy.yml. Replace your-s3-bucket-name and YOUR_CDN_ID with the S3 bucket name and CloudFront distribution ID, which can be found on the main screen for these services in the AWS console. Also replace your-region with the region your CDK stack uses.

.github/workflows/deploy.yml
name: Deploy

on:
push:
branches: [main]

jobs:
build-and-deploy:
env:
S3_BUCKET_NAME: your-s3-bucket-name
CDN_DISTRIBUTION_ID: YOUR_CDN_ID

runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v4

- uses: actions/setup-node@v4
with:
node-version: "22.x"

- run: npm ci
- run: npm run build

- uses: aws-actions/configure-aws-credentials@v4
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: your-region

- name: Upload to S3
run: aws s3 sync ./build s3://$S3_BUCKET_NAME --delete # delete files no longer in site

- name: Invalidate CDN cache
run:
aws cloudfront create-invalidation --paths "/*" --distribution-id
$CDN_DISTRIBUTION_ID
TODO

Explain how to setup the secrets

Disabling CDK deploys

If you setup a github action or some other automation and want cdk deploy to focus on infrastructure and stop deploying the site, you can delete all the code related to building and deploying from aws-infra-stack.ts. I like to comment it out just in case I quickly want to re-enable it:

aws-infra/lib/aws-infra-stack.ts
// Deploys are now handled by a Github Action, none of this is needed:
//
// const websiteDir = `${__dirname}/../..`;
//
// console.log("Building the website for deployment...");
// execSync("npm run build", { cwd: websiteDir, stdio: "inherit" });
//
// new s3deploy.BucketDeployment(this, "Deploy", {
// sources: [s3deploy.Source.asset(`${websiteDir}/build`)],
// destinationBucket: websiteBucket,
// distribution: cdn, // invalidate CDN cache
// });

With that code deleted/commented out, a cdk deploy will remove some resources from your stack that were used only for deploying (like a Lambda function and a role/permission). If you uncomment the code, those deploy resources will be recreated and a deploy will happen on the next cdk deploy.