agentleFS
AlteriomAlteriom/ai-dev-skills/skills/docker/SKILL.md

docker

Skill0 starsChanged 3 months agoMITView on GitHub

Build secure, optimized Docker containers with multi-stage builds, networking, compose orchestration, and production deployment patterns

  • Pipes a download into a shell
  • Reads credentials
  • Installs packages

55 other projects use a version of this, 2 of them edited.

Adopted by

Most recently taken up by

Used with

Projects with it also use ml-training-recipe, replication and 9 more.

Other files people use alongside this one.

Files found in the same public projects as a version of this one, more often than they turn up anywhere else. Each project counts once, large collections count for less, and this file's own repository is left out.
  • getcompanion-aiSkill

    ml-training-recipe

    Find implementable ML training recipes from papers, datasets, docs, and code. Use when the user wants to fine-tune, train, reproduce, or choose a practical ML method, dataset, hyperparameter setup, or benchmark recipe.

    Also in 3 projects that use this

  • getcompanion-aiSkill

    replication

    Plan a replication of a paper, claim, or benchmark, and execute only after an explicit environment choice. Use when the user asks to replicate results, reproduce an experiment, verify a claim empirically, or build a replication package.

    Also in 3 projects that use this

  • Sorcha-PlatformSkill

    scalar

    Generates and configures Scalar OpenAPI UI for API documentation. Use when: Adding API documentation to services, configuring OpenAPI endpoints, customizing documentation themes

    Also in 3 projects that use this

  • brainbytes-devSkill

    alpha-research

    Also in 3 projects that use this

  • JaimeParkerSkill

    paper-code-audit

    Perform three-way cross-validation of a research paper by comparing the original paper text (via Zotero), official code implementation (via Git), and personal Obsidian notes. Use this skill whenever the user wants to "audit a paper", "verify paper claims against code", "cross-check notes with implementation", "triangulate paper + code + notes", "find discrepancies between paper and code", or mentions wanting a deep, structured comparison of a paper's claims against its implementation and their own notes. Also trigger when the user asks to "analyze this paper thoroughly" with code available, or when they want to systematically reconcile what the paper says, what the code does, and what their notes claim.

    Also in 3 projects that use this

  • codewithmukeshSkill

    architecture-advisor

    Architecture selection advisor for .NET applications. Asks structured questions about domain complexity, team size, system lifetime, compliance, and integration needs, then recommends the best-fit architecture: Vertical Slice, Clean Architecture, DDD + Clean Architecture, or Modular Monolith. Load this skill when the user asks "which architecture", "choose architecture", "set up project", "new project", "architecture decision", "restructure", or "how should I organize". Always load BEFORE any architecture-specific skill.

    Also in 3 projects that use this

  • +1 more from getcompanion-ai

The file

We split this skill into the rules it gives an agent

7 rules. 0 are common, 5 are distinctive, and 2 are very specific to this project.

  • 0

    Common

    Most of the 47 edited versions we read keep these.

  • 5

    Distinctive

    This author's own choices. Worth a look.

  • 2

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Distinctive:

    Use this skill when:

    line 25
  2. Distinctive:

    Don't use: when you need:

    line 35
  3. Distinctive:

    Karpathy Principle: Simplicity First: - Start with a single Dockerfile.

    line 77
  4. Very specific:

    Karpathy Principle: Goal-Driven Execution: - After building, verify image size: docker images.

    line 168
  5. Distinctive:

    Karpathy Principle: Surgical Changes: - Use custom networks for service isolation.

    line 278
  6. Very specific:

    Karpathy Principle: Security By Design: - Never COPY secrets into images.

    line 328
  7. Distinctive:

    Wait for database health before migrations

    line 669

“Common” is measured: kept by at least 6 in 10 of the 47 edited versions of this file we could read. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
SKILL.md

Docker - Production Container Platform

When to Use

Use this skill when:

  • Containerizing applications for consistent dev/prod environments
  • Building microservices with isolation and portability
  • Deploying to Kubernetes, ECS, or container platforms
  • Creating reproducible development environments
  • Optimizing image sizes and build times
  • Managing multi-container applications with Docker Compose
  • Implementing CI/CD pipelines with containerized builds

Don't use when you need:

  • Maximum bare-metal performance (containers add ~5% overhead)
  • Kernel modules or direct hardware access
  • GUI applications (possible but complex)
  • Single static binary deployments (just ship the binary)

Karpathy Principle: Think Before Coding - Containers add complexity. If your app is a single Go binary with zero dependencies, don't containerize it. Use Docker when isolation, reproducibility, or orchestration justify the overhead.

Karpathy Principle: Trade-offs Everywhere - Containers trade 5-10% performance overhead for portability and consistency. This is worth it for 95% of apps. For hot paths (databases, caches), consider bare metal or optimized container runtimes (Kata, gVisor).

Prerequisites

Required Knowledge

  • Linux basics (processes, filesystems, networking)
  • Shell scripting (Bash/sh)
  • Understanding of application dependencies
  • Basic networking (ports, DNS, HTTP)

Required Tools

# Install Docker
curl -fsSL https://get.docker.com | sh

# Verify installation
docker --version
docker compose version

# Add user to docker group (avoid sudo)
sudo usermod -aG docker $USER
# Log out and back in for group to take effect

Project Structure

project/
├── Dockerfile
├── .dockerignore
├── docker-compose.yml
├── .env.example
└── src/

Karpathy Principle: Simplicity First - Start with a single Dockerfile. Add docker-compose only when you have 2+ services. Add Kubernetes only when Compose can't scale.

Karpathy Principle: Own Your Images - Review every layer in docker history. If you don't know what a layer does, you're vulnerable. Pin versions, audit base images, scan for CVEs.

Core Workflows

1. Dockerfile Best Practices

Node.js Multi-Stage Build:

# Build stage
FROM node:20-alpine AS builder

WORKDIR /app

# Copy package files first (cache layer)
COPY package*.json ./
RUN npm ci --only=production

# Copy source code
COPY . .
RUN npm run build

# Production stage
FROM node:20-alpine

# Security: non-root user
RUN addgroup -g 1001 -S nodejs && \
    adduser -S nodejs -u 1001

WORKDIR /app

# Copy only production files
COPY --from=builder --chown=nodejs:nodejs /app/dist ./dist
COPY --from=builder --chown=nodejs:nodejs /app/node_modules ./node_modules
COPY --chown=nodejs:nodejs package*.json ./

USER nodejs

EXPOSE 3000

# Health check
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
  CMD node -e "require('http').get('http://localhost:3000/health', (r) => process.exit(r.statusCode === 200 ? 0 : 1))"

CMD ["node", "dist/index.js"]

Python Multi-Stage Build:

FROM python:3.11-slim AS builder

WORKDIR /app

# Install dependencies in virtual environment
RUN python -m venv /opt/venv
ENV PATH="/opt/venv/bin:$PATH"

COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Production stage
FROM python:3.11-slim

# Security
RUN useradd -m -u 1001 appuser

WORKDIR /app

# Copy virtual environment
COPY --from=builder /opt/venv /opt/venv
ENV PATH="/opt/venv/bin:$PATH"

COPY --chown=appuser:appuser . .

USER appuser

EXPOSE 8000

HEALTHCHECK CMD curl --fail http://localhost:8000/health || exit 1

CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]

Key Patterns:

  • Pin versions (node:20-alpine, not node:latest)
  • Multi-stage to separate build from runtime
  • Non-root user for security
  • Health checks for orchestration
  • .dockerignore to exclude node_modules, .git, etc.

Karpathy Principle: Goal-Driven Execution - After building, verify image size: docker images. If it's >500MB for a simple app, you're doing it wrong. Use alpine, multi-stage builds, and clean up apt cache.

Karpathy Principle: Fail Fast, Fail Loud - Health checks aren't optional. Without them, orchestrators (Compose, K8s, ECS) can't detect failures. Your app might be down for minutes before you notice.

2. Docker Compose Orchestration

Full-Stack Application:

# docker-compose.yml
version: '3.8'

services:
  app:
    build:
      context: .
      dockerfile: Dockerfile
    ports:
      - "3000:3000"
    environment:
      DATABASE_URL: postgresql://postgres:${POSTGRES_PASSWORD}@db:5432/myapp
      REDIS_URL: redis://cache:6379
    depends_on:
      db:
        condition: service_healthy
      cache:
        condition: service_started
    restart: unless-stopped
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
      interval: 10s
      timeout: 5s
      retries: 3
      start_period: 40s

  db:
    image: postgres:15-alpine
    environment:
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
      POSTGRES_DB: myapp
    volumes:
      - postgres_data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U postgres"]
      interval: 5s
      timeout: 5s
      retries: 5
    restart: unless-stopped

  cache:
    image: redis:7-alpine
    command: redis-server --appendonly yes
    volumes:
      - redis_data:/data
    restart: unless-stopped

volumes:
  postgres_data:
  redis_data:

Environment File (.env):

POSTGRES_PASSWORD=your_secure_password_here

Usage:

# Start all services
docker compose up -d

# View logs
docker compose logs -f app

# Rebuild and restart
docker compose up -d --build

# Stop all services
docker compose down

# Stop and remove volumes (DESTRUCTIVE)
docker compose down -v

3. Networking

Custom Network:

services:
  app:
    networks:
      - frontend
      - backend

  db:
    networks:
      - backend

networks:
  frontend:
  backend:
    internal: true  # No external access

Host Network (for performance):

services:
  app:
    network_mode: host  # Uses host's network directly

Karpathy Principle: Surgical Changes - Use custom networks for service isolation. Internal networks prevent external access to databases. Host network mode bypasses Docker networking but loses isolation.

6. BuildKit and Advanced Build Features

Cache Mounts (faster npm/pip installs):

# syntax=docker/dockerfile:1
FROM node:20-alpine

WORKDIR /app

# Cache npm packages across builds
RUN --mount=type=cache,target=/root/.npm \
    npm ci --only=production

COPY . .
CMD ["node", "index.js"]

Build Secrets (avoid leaking credentials):

# syntax=docker/dockerfile:1
FROM alpine

# Use secret at build time without storing it in layer
RUN --mount=type=secret,id=github_token \
    git clone https://$(cat /run/secrets/github_token)@github.com/private/repo.git
# Build with secret
docker build --secret id=github_token,src=~/.github-token -t myapp .

SSH Mounts (private git repos without tokens):

# syntax=docker/dockerfile:1
FROM alpine

RUN apk add git openssh-client

# Use SSH key at build time
RUN --mount=type=ssh \
    git clone git@github.com:private/repo.git
docker build --ssh default -t myapp .

Karpathy Principle: Security By Design - Never COPY secrets into images. Use --mount=type=secret for build-time credentials. They're never stored in layers or cache.

4. Volumes and Persistence

Named Volumes (Docker-managed):

volumes:
  data:

services:
  app:
    volumes:
      - data:/app/data  # Persistent, survives container removal

Bind Mounts (host directories):

services:
  app:
    volumes:
      - ./src:/app/src:ro  # Read-only for security
      - ./uploads:/app/uploads  # Read-write

tmpfs (in-memory, fast but ephemeral):

services:
  app:
    tmpfs:
      - /tmp
      - /app/cache:size=100M

Common Patterns

1. Build Optimization

.dockerignore:

node_modules
.git
.env
*.md
.vscode
.idea
dist
build
coverage
.next

Layer Caching:

# ❌ Bad: Cache invalidated on any code change
COPY . .
RUN npm install

# ✅ Good: Cache reused if package.json unchanged
COPY package*.json ./
RUN npm install
COPY . .

2. Security Hardening

Scan for Vulnerabilities:

# Scan image
docker scout cve myapp:latest

# Scan during build
docker buildx build --sbom=true --provenance=true -t myapp .

Runtime Security:

services:
  app:
    cap_drop:
      - ALL
    cap_add:
      - NET_BIND_SERVICE
    read_only: true
    security_opt:
      - no-new-privileges:true
    tmpfs:
      - /tmp

3. Resource Limits

services:
  app:
    deploy:
      resources:
        limits:
          cpus: '1.0'
          memory: 512M
        reservations:
          cpus: '0.5'
          memory: 256M

4. Logging

JSON Logging (structured):

services:
  app:
    logging:
      driver: json-file
      options:
        max-size: "10m"
        max-file: "3"

View Logs:

docker logs -f --tail 100 myapp
docker compose logs -f --tail 100 app

5. Development vs Production

docker-compose.override.yml (auto-loaded in dev):

services:
  app:
    volumes:
      - ./src:/app/src  # Hot reload
    environment:
      - NODE_ENV=development

docker-compose.prod.yml:

services:
  app:
    restart: always
    environment:
      - NODE_ENV=production

Usage:

# Development (uses override automatically)
docker compose up

# Production
docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d

6. Init Systems for Graceful Shutdown

Problem: Docker sends SIGTERM to PID 1, but shell scripts don't forward signals.

❌ Bad (zombie processes, slow shutdown):

CMD ["sh", "-c", "npm start"]  # Shell doesn't forward SIGTERM!

✅ Good (use tini or dumb-init):

FROM node:20-alpine

# Install tini (tiny init system)
RUN apk add --no-cache tini

ENTRYPOINT ["/sbin/tini", "--"]
CMD ["node", "index.js"]  # Gets SIGTERM properly

Or use --init flag:

docker run --init myapp

Common Pitfalls

1. Image Size Bloat

❌ Bad (1GB image):

FROM node:20
WORKDIR /app
COPY . .
RUN npm install
CMD ["node", "index.js"]

✅ Good (100MB image):

FROM node:20-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci --only=production
COPY . .

FROM node:20-alpine
COPY --from=builder /app .
USER node
CMD ["node", "index.js"]

2. Secrets in Layers

❌ Bad (secret in image history):

RUN echo "API_KEY=secret" > .env

✅ Good (runtime secret):

services:
  app:
    environment:
      - API_KEY=${API_KEY}  # From .env file
    # Or use Docker secrets (Swarm/Kubernetes)

3. No Health Checks

❌ Bad:

services:
  app:
    depends_on:
      - db  # Starts app as soon as db container starts (not ready!)

✅ Good:

services:
  app:
    depends_on:
      db:
        condition: service_healthy
  db:
    healthcheck:
      test: ["CMD", "pg_isready"]
      interval: 5s

4. Running as Root

❌ Bad:

FROM node:20
WORKDIR /app
COPY . .
CMD ["node", "index.js"]  # Runs as root!

✅ Good:

FROM node:20
RUN useradd -m appuser
USER appuser
WORKDIR /app
COPY --chown=appuser:appuser . .
CMD ["node", "index.js"]

5. Port Binding Confusion

❌ Bad (binds to all interfaces):

ports:
  - "5432:5432"  # Database exposed to internet!

✅ Good (localhost only):

ports:
  - "127.0.0.1:5432:5432"  # Only accessible from host

6. Ignoring Build Context Size

❌ Bad (sends 2GB to Docker daemon):

# .dockerignore is missing or incomplete
COPY . .  # Copies node_modules, .git, etc.

✅ Good (sends 50MB):

# .dockerignore
node_modules
.git
dist
.next
coverage
*.log

Check context size: docker build --progress=plain . 2>&1 | grep 'transferring context'

Verification Checklist

Before deploying containers:

Images

  • Image < 500MB (app containers)
  • Multi-stage build used
  • Alpine/slim base images
  • No secrets in image layers
  • Version tags (not latest)

Security

  • Non-root user configured
  • Vulnerability scan passed
  • No unnecessary capabilities
  • Read-only root filesystem (if possible)

Runtime

  • Health checks defined
  • Resource limits set (memory, CPU)
  • Logging configured with rotation
  • Restart policies configured

Compose

  • .env.example committed (not .env)
  • Volumes for persistent data
  • Networks for isolation
  • depends_on with health conditions

Integration with Other Skills

With Next.js / Node.js

  • Multi-stage build with npm ci
  • Output standalone mode for minimal image
  • Health check on /api/health endpoint

With Python / FastAPI

  • Virtual environment in builder stage
  • uvicorn with proper signal handling
  • Health check on /health endpoint

With PostgreSQL / Prisma

  • Wait for database health before migrations
  • Connection pooling for container environments
  • Volumes for database persistence

With Nginx

  • Reverse proxy in front of app container
  • Static file serving from volume
  • SSL termination at proxy layer

References

Official Docs

Security

Tools

Meta: Skill Quality

Completeness: ✅ Comprehensive (9/9 sections)
Karpathy Principles: ✅ 8 mentions
Code Examples: ✅ 24+ working examples
Production Tested: ✅ Used across all Alteriom infrastructure
Last Updated: 2026-04-14

Coverage:

  • ✅ Multi-stage builds
  • ✅ Docker Compose orchestration
  • ✅ Networking and isolation
  • ✅ Volumes and persistence
  • ✅ Security hardening (secrets, SSH mounts, cache mounts)
  • ✅ Health checks
  • ✅ Resource limits
  • ✅ Development vs production
  • ✅ Image optimization
  • ✅ BuildKit advanced features
  • ✅ Init systems for graceful shutdown
  • ✅ Build context optimization

Skill Level: Intermediate
Time to Learn: 4-6 hours
Prerequisites Met: Linux basics, shell scripting

Known Gaps: None - production-ready

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.