Skip to content

Instantly share code, notes, and snippets.

@github-dorian-grasset
Last active March 5, 2026 10:56
Show Gist options
  • Select an option

  • Save github-dorian-grasset/3c0196264bd3a0337e36e476dc769201 to your computer and use it in GitHub Desktop.

Select an option

Save github-dorian-grasset/3c0196264bd3a0337e36e476dc769201 to your computer and use it in GitHub Desktop.
How I Cut Docker Image Size by Switching to a Distroless Base Image
# ---- Full Dependency and Build Stage ----
FROM node:22-alpine AS build
WORKDIR /src
COPY package*.json ./
RUN npm ci --ignore-scripts --no-fund
COPY . .
RUN npm run build:ci
# ---- Production Dependencies Stage ----
FROM node:22-alpine AS prod-deps
WORKDIR /src
COPY package*.json ./
RUN npm ci --omit=dev --ignore-scripts --no-fund
# ---- Tini Stage ----
FROM alpine:latest AS tini
ENV TINI_VERSION=v0.19.0
# Install gnupg to verify the tini signature
RUN apk add --no-cache gnupg
# Add tini binary and signature file
ARG TARGETARCH
ADD https://github.com/krallin/tini/releases/download/${TINI_VERSION}/tini-${TARGETARCH} /tini
ADD https://github.com/krallin/tini/releases/download/${TINI_VERSION}/tini-${TARGETARCH}.asc /tini.asc
# Import tini's public key and verify the binary
RUN gpg --batch --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 595E85A6B1B4779EA4DAAEC70B588DFF0527A9B7 \
&& gpg --batch --verify /tini.asc /tini \
&& chmod +x /tini
# ---- Final Production Stage ----
FROM gcr.io/distroless/nodejs22-debian12:nonroot
ENV NODE_ENV=xxxx
ENV COGNITO_POOL_ID=xxxx
ENV COGNITO_CLIENT_ID=xxxx
ENV ENVOY_GRPC_JWT_EXT_AUTHZ_PORT=xxxx
WORKDIR /src
COPY --from=prod-deps /src/node_modules ./node_modules
COPY --from=build /src/build ./build
COPY --from=tini /tini /tini
USER nonroot
ENTRYPOINT ["/tini", "--"]
CMD ["/nodejs/bin/node", "./build/index.js"]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment