Use this skill when the user asks to dockerize, containerize, or add Docker support to an application.
Steps
-
Detect the runtime — inspect
package.json,requirements.txt,go.mod,Cargo.toml, etc. to determine the language and runtime. -
Create a multi-stage
DockerfileFor Node.js (example):
FROM node:20-alpine AS base FROM base AS deps WORKDIR /app COPY package.json package-lock.json ./ RUN npm ci --omit=dev
FROM base AS build WORKDIR /app COPY package.json package-lock.json ./ RUN npm ci COPY . . RUN npm run build
FROM base AS runner WORKDIR /app ENV NODE_ENV=production COPY --from=deps /app/node_modules ./node_modules COPY --from=build /app/.next ./.next COPY --from=build /app/public ./public COPY --from=build /app/package.json ./ EXPOSE 3000 CMD ["npm", "start"]
Adapt for the detected framework — adjust the build output directory, entry command, and base image.
3. **Create `.dockerignore`**
node_modules .next .git .env* *.md
4. **Create `docker-compose.yml`** (if the app has dependencies like a database or Redis):
```yaml
services:
app:
build: .
ports:
- "3000:3000"
env_file: .env
depends_on:
- db
db:
image: postgres:16-alpine
environment:
POSTGRES_DB: app
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
volumes:
- pgdata:/var/lib/postgresql/data
volumes:
pgdata:
-
Add npm scripts (optional)
{ "docker:build": "docker build -t myapp .", "docker:run": "docker compose up" }
Notes
- Use Alpine-based images to minimize image size.
- Never copy
.envfiles into the image — useenv_fileor runtime injection. - For monorepos, use a
.dockerignorethat excludes sibling packages not needed by the target app. - Add a
HEALTHCHECKinstruction for production deployments.