feat(docker): add containerized nginx deployment with runtime base path
Two-stage build: node builds the static bundle, nginx serves it. The bundle is built against a placeholder base token that the entrypoint rewrites to $BASE_URL at start, so one image serves from any path without a rebuild. nginx config caches hashed assets forever, never caches index.html, and applies security headers (CSP, no framing, no referrer) suited to an app that handles cloud credentials client-side. .gitattributes pins LF on the container-consumed files, since core.autocrlf would otherwise give the entrypoint a CRLF shebang. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
+36
@@ -0,0 +1,36 @@
|
||||
# syntax=docker/dockerfile:1
|
||||
|
||||
# ---- Stage 1: build the static bundle ----
|
||||
FROM node:22-alpine AS build
|
||||
WORKDIR /app
|
||||
|
||||
# Deps from the lockfile first, so this layer survives source-only edits.
|
||||
COPY package.json package-lock.json ./
|
||||
RUN npm ci
|
||||
|
||||
COPY . .
|
||||
|
||||
# Build against a placeholder base. The entrypoint swaps it for $BASE_URL at startup,
|
||||
# so one image can be served from any path without rebuilding.
|
||||
RUN npm run build -- --base=/__R2B_BASE__/
|
||||
|
||||
# ---- Stage 2: serve it ----
|
||||
# Ready2Blob is entirely client-side, so the runtime image is just nginx + dist/.
|
||||
FROM nginx:alpine AS runtime
|
||||
|
||||
# Pristine copy; the entrypoint stages it into the web root on each start.
|
||||
COPY --from=build /app/dist /opt/ready2blob/html
|
||||
|
||||
COPY docker/security-headers.conf /etc/nginx/snippets/security-headers.conf
|
||||
COPY docker/nginx.conf.template /etc/nginx/ready2blob.conf.template
|
||||
COPY docker/40-ready2blob-base-url.sh /docker-entrypoint.d/40-ready2blob-base-url.sh
|
||||
RUN chmod +x /docker-entrypoint.d/40-ready2blob-base-url.sh
|
||||
|
||||
# Path the app is served from. "/" for a dedicated (sub)domain, "/ready2blob/" when
|
||||
# mounted under a path on a shared host.
|
||||
ENV BASE_URL=/
|
||||
|
||||
EXPOSE 80
|
||||
|
||||
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
|
||||
CMD wget -q --spider http://localhost/ || exit 1
|
||||
Reference in New Issue
Block a user