Building and Deploying a Single-Page Application on AWS
Creating AWS resources will incur charges if the configurations are not within the free-tier limits. Always check the AWS pricing before creating any AWS resources.
Introduction
In this tutorial, you'll learn how to create a modern single-page application (SPA) using React and Vite, and deploy it to AWS using S3 and CloudFront. Specifically, we'll set up a React project with TypeScript, configure unit tests with Vitest, add npm scripts for operational tasks, and host the static site using AWS S3 and CloudFront for CDN capabilities.
By the end of this tutorial, you will have a fully functional SPA hosted on AWS, and you'll be able to build, test, and deploy React applications efficiently using modern tools and AWS services.
Getting Started
What Is a Single-Page Application?
A single-page application (SPA) is a web application that dynamically rewrites the current page rather than loading entire new pages from a server. This approach provides a more fluid user experience, similar to that of a desktop application.
What Technologies Will We Be Using?
We'll be using the following technologies/tools in this tutorial:
- React: A JavaScript library for building user interfaces.
- Vite: A fast build tool and development server for modern web projects.
- TypeScript: A typed superset of JavaScript that compiles to plain JavaScript.
- Vitest: A blazing-fast unit testing framework powered by Vite.
- AWS S3: Amazon Simple Storage Service for storing and retrieving any amount of data.
- AWS CloudFront: A fast content delivery network (CDN) service that securely delivers data, videos, applications, and APIs to customers globally.
Prerequisites
Before you begin, make sure you have the following:
- An AWS Account: Sign up for a free AWS account if you don't have one.
- Node.js and npm Installed: Ensure you have Node.js (v14 or later) and npm installed on your machine.
- Basic Knowledge of React and TypeScript: Familiarity with React components and TypeScript syntax.
- AWS CLI Installed and Configured: Set up the AWS Command Line Interface with your credentials.
Steps
We'll follow these steps to build and deploy our application:
- Initialize the React Project with Vite: Set up a new React project using Vite with TypeScript support.
- Set Up Unit Tests with Vitest: Configure Vitest for testing our React components.
- Add npm Scripts for Operational Tasks: Streamline tasks like building, testing, and deploying.
- Host the Static Site on AWS S3: Upload and configure our site on Amazon S3.
- Configure AWS CloudFront as a CDN: Set up CloudFront to deliver our content globally.
Important: Creating AWS resources will incur charges if the configurations are not within the free-tier limits. Always check the AWS pricing before creating any AWS resources.
Step 1: Initialize the React Project with Vite
In this step, we'll create a new React application using Vite and set up TypeScript support.
Instructions:
-
Create a New Vite Project
-
Open your terminal and run the following command:
bashLoading...- This command initializes a new Vite project named
my-spa
using the React TypeScript template. - Replace
my-spa
with your desired project name.
- This command initializes a new Vite project named
-
-
Install Dependencies
-
Navigate to the project directory and install the required packages:
bashLoading...
-
-
Start the Development Server
-
Run the development server:
bashLoading... -
Open your browser and navigate to
http://localhost:5173
to see the default React application running.
-
Step 2: Set Up Unit Tests with Vitest
We'll configure Vitest to enable unit testing for our React components.
Instructions:
-
Install Vitest and Testing Libraries
-
Install Vitest and related packages:
bashLoading...
-
-
Configure Vitest in
vite.config.ts
-
Open
vite.config.ts
and modify it to include Vitest configuration:typescriptLoading...
-
-
Create a Test Setup File
-
Create a new file at
src/setupTests.ts
and add:typescriptLoading...
-
-
Write a Sample Test
-
Create
src/App.test.tsx
with the following content:typescriptLoading...- This test checks for the presence of the "Vite + React" text in the rendered
App
component.
- This test checks for the presence of the "Vite + React" text in the rendered
-
-
Update npm Scripts
-
In
package.json
, add a test script:jsonLoading...
-
-
Run the Tests
-
Execute:
bashLoading... -
You should see the test results in your terminal.
-
Step 3: Add npm Scripts for Operational Tasks
We'll add scripts to automate common tasks like deploying the application to AWS.
Instructions:
-
Add Deploy Script
-
In the
scripts
section ofpackage.json
, add a deploy script:jsonLoading...- Replace
YOUR_BUCKET_NAME
with the name of your S3 bucket. - Explanation: The command
aws s3 sync dist/ s3://YOUR_BUCKET_NAME --delete
synchronizes the contents of your localdist/
directory (the build output) with the specified S3 bucket. The--delete
flag ensures that files not present indist/
are removed from the bucket, keeping it in sync with your local build.
- Replace
-
Step 4: Host the Static Site on AWS S3
We'll create an S3 bucket and configure it for static website hosting without making it publicly accessible.
Instructions:
-
Create an S3 Bucket
-
Run the following command to create a new S3 bucket:
bashLoading...- Replace
YOUR_BUCKET_NAME
with a globally unique name andYOUR_REGION
with your AWS region (e.g.,us-east-1
).
- Replace
-
-
Build the Application
-
Build your project:
bashLoading...
-
-
Deploy to S3
-
Run the deploy script:
bashLoading... -
This command uploads your build files to the S3 bucket.
-
-
Configure S3 Bucket for CloudFront Access
- We will configure the bucket policy to allow CloudFront to access the bucket contents securely.
Step 5: Configure AWS CloudFront as a CDN
We'll set up CloudFront to deliver our content globally and securely access the S3 bucket using AWS CLI commands.
Instructions:
-
Create an Origin Access Control (OAC)
-
CloudFront uses an Origin Access Control to securely access the S3 bucket.
-
Create an OAC:
bashLoading...- Note the
Id
of the created OAC from the output.
- Note the
-
-
Create a CloudFront Distribution
-
Create a JSON file named
distribution-config.json
with the following content (replace placeholders with your values):jsonLoading...- Replace
YOUR_BUCKET_NAME
with your actual bucket name. - Replace
YOUR_OAC_ID
with theId
of the Origin Access Control you created earlier. - Adjust the
CallerReference
as needed to ensure uniqueness.
- Replace
-
Create the CloudFront distribution:
bashLoading...- Note the
Id
andDomainName
of the created distribution.
- Note the
-
-
Update S3 Bucket Policy
-
Create a bucket policy JSON file named
bucket-policy.json
:jsonLoading...- Replace
YOUR_BUCKET_NAME
,YOUR_ACCOUNT_ID
, andYOUR_DISTRIBUTION_ID
with your actual values.
- Replace
-
Apply the bucket policy:
bashLoading...
-
-
Test Your CloudFront Distribution
-
Wait for the distribution status to become Deployed. This may take several minutes.
-
Access your website using the CloudFront domain name provided (e.g.,
d1234abcdefg.cloudfront.net
).
-
-
Invalidate Cache After Deployment
-
Add an invalidate script to
package.json
:jsonLoading...- Replace
YOUR_DISTRIBUTION_ID
with your CloudFront distribution ID.
- Replace
-
Run the script after deployments to ensure users receive the latest content:
bashLoading...
-
Conclusion
Congratulations! You've successfully built a modern React single-page application with TypeScript, set up unit testing with Vitest, and deployed it to AWS using S3 and CloudFront. You now know how to set up a React project with Vite, write unit tests, and host your application on AWS for global access.
Customizing the Project
You can further enhance this project by:
- Adding More Features: Implement additional components or integrate with APIs.
- Setting Up Continuous Deployment: Use CI/CD pipelines for automatic deployments.
- Enhancing Performance: Optimize your app using code-splitting and lazy loading.
Next Steps
To continue learning:
- Explore Advanced Vite Features: Learn about plugins and custom configurations.
- Dive Deeper into AWS Services: Look into AWS Amplify or AWS Lambda for serverless functions.
- Improve Testing: Add integration and end-to-end tests using tools like Cypress.
Reference
Here's a summary of the commands and code used throughout this tutorial for your convenience.
Commands and Code Snippets
Additional Resources
- React Documentation: React Official Docs
- Vite Documentation: Vite Official Docs
- Vitest Documentation: Vitest Official Docs
- AWS CLI Command Reference: AWS CLI Documentation
- AWS S3 Static Website Hosting: AWS S3 Hosting Guide
- AWS CloudFront: AWS CloudFront Developer Guide
Remember to always check the AWS pricing and free-tier limits to avoid unexpected charges.