# ---- Stage 1: build static assets ---- # The frontend was fully rewritten from scratch under web/ (Vite + React + TS) on branch # redesign/desktop-multicolumn, merged into dev 2026-09-09 -- this replaces the old webpack build # that used to live at the repo root (umd/, css/base.min.css, index.html, etc.). See web/README- # equivalent context in the redesign plan for why: this Dockerfile previously never touched web/ at # all, so every "deploy" kept shipping the old app regardless of what was on dev. FROM node:22-alpine AS build WORKDIR /app/web COPY web/package.json web/package-lock.json ./ RUN npm ci COPY web/. . # VITE_TINODE_API_KEY is read by src/lib/config.ts (import.meta.env.VITE_TINODE_API_KEY) at build # time -- Vite only exposes env vars prefixed VITE_ to client code, so the ARG is renamed on its # way into the build's environment rather than passed through under its old webpack-era name. ARG TINODE_API_KEY= ENV VITE_TINODE_API_KEY=$TINODE_API_KEY RUN npm run build # ---- Stage 2: serve with nginx ---- FROM nginx:alpine COPY docker/nginx.conf /etc/nginx/conf.d/default.conf WORKDIR /usr/share/nginx/html # Vite's build output is fully self-contained: index.html + favicon.svg/icons.svg (from web/public/, # copied verbatim) + assets/ (content-hashed JS/CSS chunks) -- no separate umd/css/img/audio/ # manifest/service-worker/firebase files the way the old build had, none of that machinery exists # in the new app. COPY --from=build /app/web/dist/. ./ HEALTHCHECK --interval=1m --timeout=3s --start-period=10s \ CMD wget -q -O /dev/null http://localhost/ || exit 1 EXPOSE 80