Automating static site deployment on every Git push eliminates manual build/upload steps and ensures your live site always reflects your latest committed changes. This guide covers setting this up with GitHub Actions.
Why Automate Static Site Deployment
See How to Set Up Automatic Static Site Deployment from Git for the general webhook-based pattern — GitHub Actions provides a more integrated, feature-rich alternative, particularly valuable if your build process involves multiple steps (linting, testing, building) beyond a simple file copy.
Step 1 — Create the Workflow File
mkdir -p .github/workflows
nano .github/workflows/deploy.yml
Step 2 — Define the Build and Deploy Workflow
name: Deploy Static Site
on:
push:
branches: [main]
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
- run: npm install
- run: npm run build
- name: Deploy to VPS
uses: appleboy/[email protected]
with:
host: ${{ secrets.VPS_HOST }}
username: ${{ secrets.VPS_USER }}
key: ${{ secrets.VPS_SSH_KEY }}
source: "dist/*"
target: "/var/www/mysite"
Builds the site, then securely copies the output to your VPS via SSH — see How to Manage Secrets in a CI/CD Pipeline for properly configuring the required secrets.
Step 3 — Set Up Required Secrets in GitHub
In repository Settings > Secrets and variables > Actions, add VPS_HOST, VPS_USER, and VPS_SSH_KEY — never hardcode these values directly in the workflow file.
Step 4 — Create a Dedicated Deployment SSH Key
See How to Set Up a Deployment User with Restricted SSH Access — use a dedicated key/user with minimal necessary permissions for the deployment target directory only, rather than a broadly-privileged account.
Adding a Build Verification Step
- name: Check for broken links
run: npx linkinator dist --recurse
Consider adding basic verification steps (broken link checking, HTML validation) before deployment, catching issues before they reach your live site.
Setting Up Preview Deployments for Pull Requests
See How to Set Up Preview Deployments for Pull Requests — extend this workflow pattern to also deploy PR branches to a temporary preview location, letting you review changes before merging to main.
Notifying on Deployment Success/Failure
- name: Notify on failure
if: failure()
run: curl -X POST YOUR_WEBHOOK_URL -d "Deployment failed"
Reloading Nginx After File Updates (If Needed)
- name: Reload Nginx
uses: appleboy/[email protected]
with:
host: ${{ secrets.VPS_HOST }}
script: sudo systemctl reload nginx
Usually unnecessary for pure static files (Nginx serves updated files immediately), but relevant if your deployment also touches Nginx configuration.
Common Errors
SCP/SSH action fails with permission denied — verify the deployment user's SSH key is correctly added to the target server's authorized_keys, and that the target directory has appropriate write permissions for that user.
Continue Reading
- How to Set Up Automatic Static Site Deployment from Git
- How to Set Up Preview Deployments for Pull Requests
- How to Manage Secrets in a CI/CD Pipeline
Browse more articles in Static Site Hosting & Frontend Deployment.