Docker Compose Generator — Free Online Tool

Generate docker-compose.yml files for multi-container apps with services, networks, volumes and environment variables. Includes common templates.

Use this free online Docker Compose Generator directly in your browser. No signup required, no data leaves your device. Part of Utilier — a collection of 133+ developer utilities.

What is Docker Compose Generator (YAML Configuration)?

Docker Compose generator creates YAML configuration files (docker-compose.yml) to orchestrate multi-container Docker applications. Define services (Node.js app, PostgreSQL database, Redis cache, Nginx reverse proxy), configure networks (bridge, host), volumes (persistent data), environment variables, ports, dependencies, and health checks. Tool generates production-ready compose files with best practices: named volumes for data persistence, service dependencies (depends_on), resource limits (CPU, memory), restart policies (unless-stopped), and security settings (read-only file systems, non-root users). Useful for local development (replicate production environment), microservices (multiple services in one file), or learning Docker orchestration (service networking, volume management).

  • Service templates: Pre-configured services: Node.js/Express (web app), PostgreSQL (database), MySQL, MongoDB, Redis (cache), Nginx (reverse proxy), Python/Flask, PHP/Apache. Customize ports, environment variables, volumes.
  • Network configuration: Create custom networks (bridge, overlay), connect services (app → database), isolate services (separate networks for frontend/backend). Networks enable service-to-service communication by name.
  • Volume management: Named volumes (postgres-data, app-logs) for persistent data, bind mounts (./app:/usr/src/app) for development hot-reload, tmpfs for temporary data. Volumes survive container restarts.
  • Environment variables: Set env vars: DATABASE_URL, API_KEY, NODE_ENV. Use .env file (env_file: .env) or inline (environment: NODE_ENV=production). Secrets management for sensitive data.
  • Dependencies and orchestration: Service dependencies (depends_on: db), health checks (wait for database ready), restart policies (restart: unless-stopped), build contexts (build: ./app).

Why use docker compose?

Writing docker-compose.yml manually is complex (YAML syntax, service networking, volume configuration). This tool generates valid, production-ready compose files.

  • Avoid YAML errors: YAML is indentation-sensitive (spaces, not tabs). Wrong indentation = syntax error. Tool validates and generates correct YAML.
  • Multi-container orchestration: Run entire stack (app + database + cache + proxy) with one command: docker-compose up. No need to run multiple docker run commands.
  • Development environment: Replicate production locally. Same database version, same dependencies, same network setup. Eliminates 'works on my machine' issues.
  • Microservices architecture: Define multiple services (API, frontend, database, queue) in one file. Service discovery by name (api connects to postgres by hostname 'postgres').
  • Learn Docker networking: See how services communicate (custom networks), share data (volumes), and depend on each other (depends_on). Great for learning Docker.
  • Best practices built-in: Tool adds: resource limits (prevent OOM), health checks (wait for database), restart policies (auto-restart on crash), security (non-root users).

When to use docker compose

Use whenever you need to run multi-container Docker applications.

  • Local development (run full stack: app + database + cache with docker-compose up).
  • Microservices development (multiple services: API, frontend, database, Redis, Nginx).
  • Testing environments (isolated environments for integration tests, CI/CD pipelines).
  • Learning Docker orchestration (service networking, volumes, dependencies).
  • Deploying to Docker Swarm or Kubernetes (convert compose to swarm stack or k8s).
  • Documentation (share development environment setup with team via compose file).
  • Database + app stacks (WordPress + MySQL, Django + PostgreSQL, MERN stack).

How to use docker compose

Select services, configure options, generate docker-compose.yml.

  1. Add services: Select service type: Node.js, PostgreSQL, MySQL, MongoDB, Redis, Nginx, Python, PHP. Configure image version, ports, environment variables.
  2. Configure networks (optional): Create custom networks (frontend, backend). Connect services to networks. Example: app and nginx on frontend, app and database on backend.
  3. Add volumes (optional): Named volumes for persistent data (postgres-data), bind mounts for development (./app:/usr/src/app). Volumes survive container restarts.
  4. Set environment variables: Inline (environment: DATABASE_URL=postgres://...) or .env file (env_file: .env). Use for config, API keys, database URLs.
  5. Configure dependencies: Set depends_on (app depends on database). Ensures database starts before app. Add health checks to wait for database ready.
  6. Set resource limits (optional): CPU (cpus: 0.5), memory (mem_limit: 512m). Prevents one service from consuming all resources.
  7. Generate YAML: Click Generate to get docker-compose.yml. Save to project root. Run: docker-compose up (start all services), docker-compose down (stop and remove).

Key features

  • Service templates: Node.js, PostgreSQL, MySQL, MongoDB, Redis, Nginx, Python, PHP. Pre-configured with best practices.
  • Custom networks: Bridge (default), overlay (Swarm), host. Service-to-service communication by name.
  • Volume management: Named volumes (persistent data), bind mounts (development), tmpfs (temporary). Survives container restarts.
  • Environment variables: Inline or .env file. Secrets management for sensitive data (passwords, API keys).
  • Dependencies: depends_on (start order), health checks (wait for ready), restart policies (unless-stopped, always, on-failure).
  • Resource limits: CPU (cpus), memory (mem_limit), reservations (guaranteed resources). Prevents resource exhaustion.
  • Security settings: Read-only file systems (read_only: true), non-root users (user: 1000), no new privileges (security_opt: no-new-privileges).

Common use cases

  • Node.js + PostgreSQL: Web app (Node.js on port 3000) + database (PostgreSQL on port 5432). Volumes: postgres-data (persistent), ./app:/app (hot-reload). Network: app connects to postgres by hostname 'postgres'.
  • MERN stack: MongoDB (database), Express (API), React (frontend), Node.js (runtime). Nginx reverse proxy (frontend on /, API on /api). All services in one compose file.
  • WordPress + MySQL: WordPress (PHP on port 8080) + MySQL (database on port 3306). Volumes: wordpress-data, mysql-data. Environment: WORDPRESS_DB_HOST=mysql, WORDPRESS_DB_PASSWORD.
  • Microservices (API + Redis): API service (Node.js) + Redis (cache). API uses Redis for session storage. depends_on: redis. Restart: unless-stopped (auto-restart on crash).
  • Development with hot-reload: Bind mount ./app:/app. Edit code locally → container sees changes immediately (nodemon or webpack dev server watches for changes). No rebuild needed.
  • Nginx reverse proxy: Nginx proxies requests to backend services (proxy_pass http://api:3000). SSL termination, static file serving, load balancing. Frontend on port 80, backend on internal network.

Examples

Docker Compose configurations.

Node.js + PostgreSQL

Services: Node.js app (port 3000), PostgreSQL (port 5432)
version: '3.8'
services: app: image: node:20-alpine ports: - '3000:3000' environment: DATABASE_URL: postgres://postgres:password@postgres:5432/mydb depends_on: - postgres postgres: image: postgres:15-alpine environment: POSTGRES_PASSWORD: password volumes: - postgres-data:/var/lib/postgresql/data
volumes: postgres-data:

App connects to postgres by hostname 'postgres'. Named volume postgres-data persists database. Run: docker-compose up.

Nginx reverse proxy

Services: Nginx (port 80), API (port 3000)
version: '3.8'
services: nginx: image: nginx:alpine ports: - '80:80' volumes: - ./nginx.conf:/etc/nginx/nginx.conf:ro depends_on: - api api: image: node:20-alpine expose: - 3000

Nginx proxies to api (proxy_pass http://api:3000). API not exposed to host (only Nginx). Read-only nginx.conf.

Development with hot-reload

Services: Node.js app with bind mount
version: '3.8'
services: app: build: . ports: - '3000:3000' volumes: - ./app:/usr/src/app - /usr/src/app/node_modules command: npm run dev

Bind mount ./app:/usr/src/app for hot-reload. Exclude node_modules (use container's version). nodemon watches for changes.

Resource limits

Services: App with CPU and memory limits
version: '3.8'
services: app: image: node:20-alpine deploy: resources: limits: cpus: '0.5' memory: 512M reservations: cpus: '0.25' memory: 256M

Limits: max 0.5 CPU, 512 MB RAM. Reservations: guaranteed 0.25 CPU, 256 MB. Prevents resource exhaustion.

Health checks

Services: Database with health check
version: '3.8'
services: app: image: node:20-alpine depends_on: postgres: condition: service_healthy postgres: image: postgres:15-alpine healthcheck: test: ['CMD', 'pg_isready', '-U', 'postgres'] interval: 10s timeout: 5s retries: 5

App waits for postgres to be healthy (pg_isready succeeds). Ensures database is ready before app starts.

Technical reference

Docker Compose YAML structure (version 3.8+):

version
Compose file version: 3.8 (latest for Compose standalone), 3.9 (experimental). Version 2 is legacy. Use 3.8 for production.
services
Define containers: service_name: { image, ports, environment, volumes, networks, depends_on }. Example: app: { image: node:20, ports: ['3000:3000'] }.
image vs build
image: node:20 (use existing image from Docker Hub). build: ./app (build from Dockerfile in ./app). Use build for custom images, image for official images.
ports
Port mapping: HOST:CONTAINER. Example: ports: ['8080:80'] (host port 8080 → container port 80). Or long syntax: ports: [{ target: 80, published: 8080, protocol: tcp }].
environment
Environment variables: environment: { NODE_ENV: production, DATABASE_URL: postgres://... }. Or env_file: .env (load from file). Secrets: use secrets: instead.
volumes
Named volumes: volumes: [postgres-data:/var/lib/postgresql/data]. Bind mounts: volumes: ['./app:/app']. tmpfs: tmpfs: [/tmp]. Top-level volumes: must declare named volumes.
networks
Custom networks: networks: [frontend, backend]. Service connects to networks. Top-level networks: must declare. Default: bridge network (all services).
depends_on
Service dependencies: depends_on: [db, redis]. Starts dependencies first. Does NOT wait for ready (use health checks). Short syntax: depends_on: [db]. Long: depends_on: { db: { condition: service_healthy } }.
restart
Restart policy: no (never), always (always restart), on-failure (restart on error), unless-stopped (restart unless manually stopped). Production: unless-stopped.
healthcheck
Health check: healthcheck: { test: ['CMD', 'curl', '-f', 'http://localhost'], interval: 30s, timeout: 10s, retries: 3 }. Use with depends_on: { condition: service_healthy }.

Common mistakes to avoid

Using tabs instead of spaces in YAML (causing parse errors)

Why it happens: YAML requires spaces for indentation, not tabs. Tabs cause 'mapping values are not allowed here' errors. Common when copy-pasting or using some editors.

How to avoid it: Configure editor to use spaces (2 spaces per indent level). Or use tool to generate YAML (always uses spaces). Run: docker-compose config to validate.

Not declaring named volumes at top level (causing volume creation failure)

Why it happens: Named volumes (postgres-data) must be declared in top-level volumes: section. Service-level volumes: [postgres-data:/path] references it. Without top-level declaration, Docker Compose errors.

How to avoid it: Add top-level: volumes: postgres-data: (empty config uses defaults). Or volumes: postgres-data: { driver: local }. Then reference in service: volumes: [postgres-data:/var/lib/postgresql/data].

Using localhost in environment variables instead of service names

Why it happens: DATABASE_URL=postgres://localhost:5432 fails (localhost = container itself, not host). Services use custom network, communicate by service name. Use DATABASE_URL=postgres://postgres:5432 (postgres = service name).

How to avoid it: Use service name as hostname: postgres, redis, mysql. Docker Compose creates DNS entries for service names. localhost = current container. host.docker.internal = host machine.

Not using depends_on, causing race conditions (app starts before database)

Why it happens: Without depends_on, all services start simultaneously. App tries to connect to database before it's ready → connection error. Common with databases (slow startup).

How to avoid it: Add depends_on: [postgres] to app service. Better: use health checks (depends_on: { postgres: { condition: service_healthy } }). Waits for database to be ready.

Hardcoding secrets (passwords, API keys) in compose file, committing to git

Why it happens: Exposing secrets in git = security vulnerability. Anyone with repo access sees passwords. Common when using public repos or shared repos.

How to avoid it: Use .env file (env_file: .env) for secrets. Add .env to .gitignore. Or use Docker secrets (secrets: db_password). Commit compose file with placeholders, not actual secrets.

Frequently asked questions

What is the difference between docker-compose and docker compose?

docker-compose = standalone tool (Python, legacy). docker compose = Docker CLI plugin (Go, modern). Same functionality, different commands. Use docker compose (built into Docker Desktop).

How do services communicate with each other?

By service name as hostname. Example: app connects to postgres://postgres:5432 (postgres = service name). Docker Compose creates custom network with DNS for service discovery.

What is the difference between volumes and bind mounts?

Named volumes (postgres-data): managed by Docker, persist data. Bind mounts (./app:/app): map host directory to container. Use volumes for data, bind mounts for development (hot-reload).

How do I run docker-compose in background?

docker-compose up -d (detached mode). Services run in background. View logs: docker-compose logs -f. Stop: docker-compose down.

What is depends_on and why doesn't it wait for database ready?

depends_on controls start order (database starts before app) but doesn't wait for ready. Add health check: depends_on: { postgres: { condition: service_healthy } }. Waits for health check to pass.

How do I rebuild images after code changes?

docker-compose up --build (rebuild and start). Or docker-compose build (rebuild only). Use for build: ./app services (not image: node:20).

Can I use docker-compose for production?

Yes, but Docker Swarm or Kubernetes are better for production (scaling, high availability). docker-compose works for single-server deployments. Convert to swarm: docker stack deploy.

References

Privacy and availability

  • Runs entirely in your browser — zero server processing
  • No signup or account required
  • Works offline once loaded
  • Fast, lightweight, no external dependencies
  • Available as a browser extension for Chrome and Firefox