Add Docker deployment for mcwaddams.mcp.website

Multi-stage build: Node 22 for Astro build, Caddy 2 Alpine for
static file serving. Reverse-proxied via caddy-docker-proxy.
This commit is contained in:
Ryan Malloy 2026-02-14 12:57:51 -07:00
parent e537ddcda6
commit 3af91e8a9d
6 changed files with 101 additions and 0 deletions

7
.dockerignore Normal file
View File

@ -0,0 +1,7 @@
node_modules
dist
.astro
.git
.env
.env.*
!.env.example

2
.env.example Normal file
View File

@ -0,0 +1,2 @@
COMPOSE_PROJECT_NAME=mcwaddams-site
DOMAIN=mcwaddams.mcp.website

24
Caddyfile Normal file
View File

@ -0,0 +1,24 @@
:8080 {
root * /srv
file_server
handle /health {
respond "OK" 200
}
# SPA-style fallback for clean URLs
try_files {path} {path}/ {path}.html /index.html
# Cache static assets aggressively
@static path *.css *.js *.svg *.png *.webp *.jpg *.jpeg *.gif *.ico *.woff *.woff2
header @static Cache-Control "public, max-age=31536000, immutable"
# Security headers
header {
X-Content-Type-Options "nosniff"
X-Frame-Options "DENY"
Referrer-Policy "strict-origin-when-cross-origin"
}
encode gzip zstd
}

21
Dockerfile Normal file
View File

@ -0,0 +1,21 @@
# Stage 1: Build the Astro/Starlight site
FROM node:22-alpine AS build
WORKDIR /app
COPY package.json package-lock.json* ./
RUN npm ci
COPY . .
RUN npm run build
# Stage 2: Serve static files with Caddy
FROM caddy:2-alpine
COPY --from=build /app/dist /srv
COPY Caddyfile /etc/caddy/Caddyfile
EXPOSE 8080
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
CMD wget -qO- http://127.0.0.1:8080/health || exit 1

28
Makefile Normal file
View File

@ -0,0 +1,28 @@
.PHONY: build up down restart logs status clean
build:
docker compose build
up: build
docker compose up -d
@echo "Waiting for container to start..."
@sleep 3
docker compose logs --tail=20
down:
docker compose down
restart:
docker compose down
docker compose up -d --build
@sleep 3
docker compose logs --tail=20
logs:
docker compose logs -f
status:
docker compose ps
clean:
docker compose down --rmi local --volumes

19
docker-compose.yml Normal file
View File

@ -0,0 +1,19 @@
services:
site:
build: .
restart: unless-stopped
networks:
- caddy
labels:
caddy: ${DOMAIN}
caddy.reverse_proxy: "{{upstreams 8080}}"
healthcheck:
test: ["CMD", "wget", "-qO-", "http://127.0.0.1:8080/health"]
interval: 30s
timeout: 3s
start_period: 5s
retries: 3
networks:
caddy:
external: true