open-weight/skills/dockerfile/SKILL.md
Use when writing, reviewing, or editing a Dockerfile or docker-compose file. Use when asked to "containerize", "dockerize", "add Docker support", or "write a Dockerfile" for any application or service.
npx skillsauth add jon23d/skillz dockerfileInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Every Dockerfile decision affects security, build speed, and image size. Apply these rules without exception.
This project is Node.js / TypeScript. Read node.md before writing any code.
Never use latest. Pin to a specific version tag. Prefer minimal variants.
# Bad
FROM node:latest
# Good
FROM node:22.3-slim
Use -slim or -alpine variants unless you have a specific reason not to. Alpine is smallest but can cause compatibility issues with native binaries — use -slim when unsure.
If the project has a .tool-versions, package.json engines, or equivalent, match the pinned version there.
Docker caches layers. A changed layer invalidates all layers below it. Order from least-to-most frequently changing:
# Bad — source code copied before deps; deps reinstall on every code change
COPY . .
RUN npm install
# Good — deps installed before source; cache survives code changes
COPY package.json package-lock.json ./
RUN npm install
COPY . .
Rule: copy only what's needed for the next step. Don't COPY . . until after all dependency installs.
Use multi-stage builds to keep dev dependencies and build artifacts out of the production image.
# Stage 1: build
FROM node:22.3-slim AS builder
WORKDIR /app
COPY package.json package-lock.json ./
RUN npm ci
COPY . .
RUN npm run build
# Stage 2: production
FROM node:22.3-slim AS production
WORKDIR /app
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/node_modules ./node_modules
The final stage should contain only what's needed to run the application.
Secrets in ENV or ARG instructions are visible in the image history.
# Bad — secret visible in `docker history`
ARG NPM_TOKEN
RUN echo "//registry.npmjs.org/:_authToken=${NPM_TOKEN}" > .npmrc
RUN npm install
# Good — secret used only during build, not stored in layer
RUN --mount=type=secret,id=npm_token \
NPM_TOKEN=$(cat /run/secrets/npm_token) \
npm install
For runtime secrets, use environment variables injected at runtime — never hardcoded in the Dockerfile.
# Add at the end of your final stage, before CMD
RUN addgroup --system appgroup && adduser --system --ingroup appgroup appuser
USER appuser
Some base images (e.g. node:slim) include a default non-root user — use it:
USER node
Without .dockerignore, the entire build context is sent to the daemon, including secrets, dev files, and .git.
Minimum .dockerignore:
.git
.env
*.env
node_modules
__pycache__
.DS_Store
Add any build artifacts, test output, or local config that shouldn't be in the image.
Orchestrators (Kubernetes, ECS, Docker Swarm) use HEALTHCHECK to detect unhealthy containers. Without it, a crashed app inside a running container looks healthy.
HEALTHCHECK --interval=30s --timeout=5s --start-period=10s --retries=3 \
CMD curl -f http://localhost:8080/health || exit 1
Adjust the path and port to match your application's actual port. If the app doesn't have an HTTP health endpoint, add one.
After building, check the image size:
docker images <image-name>
docker history <image-name> # shows which layers are largest
If the image is unexpectedly large:
RUN step that installs:RUN apt-get update && apt-get install -y --no-install-recommends \
curl \
&& rm -rf /var/lib/apt/lists/*
node.md)ENV, ARG, or RUN commands.dockerignore created and includes .git, .env, build artifactsHEALTHCHECK defined with appropriate path and intervaldocker images after builddevelopment
Use when adding or modifying environment variable handling in TypeScript projects or monorepos — especially when using process.env directly, missing startup validation, sharing env schemas across packages, or encountering "undefined is not a string" errors at runtime from missing env vars.
testing
Use when creating a new skill, editing an existing skill, writing a SKILL.md, or verifying a skill works before deployment.
development
React UI design principles and conventions. Load when building or modifying any user interface or React components. Covers application type detection, visual standards, component design and structure, Mantine (business apps) and Tailwind (consumer apps), accessibility, responsiveness, state management, data fetching, testing, and in-app help patterns.
development
Use when setting up ESLint and/or Prettier in a TypeScript project, adding linting to an existing TypeScript codebase, or configuring typescript-eslint, eslint-config-prettier, or related packages.