Skip to main content

Chat Docker Compose (Stage 6)

Multi-container deployment with Docker Compose


Overview

This example takes the fullstack chat application and containerizes it with Docker. A Traefik reverse proxy routes requests to a Caddy-served React frontend and an Express backend, with PostgreSQL for persistence — all orchestrated by Docker Compose.

Why this matters:

  • Understand containerization (Dockerfiles, images, containers)
  • Learn multi-stage builds for production-optimized images
  • See how reverse proxies route traffic between services
  • Foundation for Kubernetes and production deployments

What You'll Learn

  • Dockerfiles: Writing production-ready containers for Node.js and React
  • Multi-Stage Builds: Build stage (Node) → serve stage (Caddy) for tiny images
  • Docker Compose: Defining multi-container applications declaratively
  • Traefik: Label-based reverse proxy with path routing
  • Container Networking: Service discovery via DNS names
  • Volume Persistence: Surviving database restarts

Prerequisites


Project Structure

19-chat-docker-compose/
├── client/
│ ├── Dockerfile # Multi-stage: Node (build) → Caddy (serve)
│ ├── Caddyfile # SPA routing config
│ └── src/ # React application
├── server/
│ ├── Dockerfile # Node.js production image
│ └── src/ # Express API (PostgreSQL)
├── docker-compose.yml # Traefik + services
├── docker-compose.override.yml # Dev overrides (live reload)
└── .env.example

Quick Start

cd examples/19-chat-docker-compose

# Production-like mode (Traefik + Caddy + Node + Postgres)
docker compose -f docker-compose.yml up --build

# Development mode (with live reload)
docker compose up --build
  • App: http://localhost:8080
  • Traefik dashboard: http://localhost:8081

Key Concepts

1. Multi-Stage Dockerfile

Build your React app, then serve static files with Caddy — no Node.js in the final image:

FROM node:20-alpine AS build
WORKDIR /app
COPY package.json package-lock.json ./
RUN npm ci
COPY . .
RUN npm run build

FROM caddy:2-alpine
COPY Caddyfile /etc/caddy/Caddyfile
COPY --from=build /app/dist /srv

2. Traefik Reverse Proxy

Traefik reads Docker labels to route traffic — no config files needed:

backend:
labels:
- "traefik.enable=true"
- "traefik.http.routers.backend.rule=PathPrefix(`/api`)"
- "traefik.http.routers.backend.priority=2"

3. Architecture

Browser → :8080 → Traefik
├── /api/* → Backend (Express :3001)
│ └── PostgreSQL (:5432)
└── /* → Frontend (Caddy :80)

Curriculum Alignment

This example aligns with:

  • Module 19: Containerization & Orchestration — Docker and Docker Compose

Next Steps

Ready for Kubernetes? Continue to Chat Kubernetes.


Source Code

View the complete source: examples/19-chat-docker-compose/