Skip to content

Fix: docker-compose.override.yml Not Working — Override File Ignored or Not Merged

FixDevs ·

Quick Answer

How to fix docker-compose.override.yml not being applied — file naming, merge behavior, explicit file flags, environment-specific configs, and common override pitfalls.

The Problem

A docker-compose.override.yml file exists but its settings aren’t applied:

# docker-compose.override.yml — expected to add volume mount
services:
  app:
    volumes:
      - ./src:/app/src
    environment:
      DEBUG: "true"
docker compose up
# Container starts without the volume mount or DEBUG env var
# Override file is silently ignored

Or an explicit -f flag stops the override from loading:

docker compose -f docker-compose.yml up
# Only docker-compose.yml loaded — override.yml skipped entirely

Or multiple override files conflict:

docker compose -f docker-compose.yml -f docker-compose.prod.yml up
# docker-compose.override.yml NOT loaded — explicit -f disables auto-loading

Why This Happens

Docker Compose has an auto-merge feature: when you run docker compose up with no -f flags, it automatically merges docker-compose.yml with docker-compose.override.yml if both files exist in the current directory.

This auto-merge only happens under specific conditions:

  • Exact filename required — the file must be named docker-compose.override.yml (not docker-compose.override.yaml, not override.yml). The .yml extension is required, not .yaml, unless your base file uses .yaml.
  • Must be in the same directory — both files must be in the same directory where you run docker compose.
  • -f flag disables auto-loading — as soon as you use -f to specify any file, Docker Compose stops auto-loading and only uses the files you explicitly listed.
  • Docker Compose v1 vs v2docker-compose (v1, Python) vs docker compose (v2, Go plugin) have minor behavioral differences. Some older setups use docker-compose.yml only and don’t support override files in the same way.

Fix 1: Verify the Filename and Location

The override file must be named exactly docker-compose.override.yml:

# Check what files exist
ls -la docker-compose*.yml docker-compose*.yaml 2>/dev/null

# Correct filename
docker-compose.override.yml
docker-compose.override.yaml (wrong extension if base is .yml)
docker.compose.override.yml (dot instead of hyphen)
override.yml (wrong name)
docker-compose-override.yml (hyphen instead of dot before override)

Verify Compose is actually reading both files:

# Print the merged config — shows what Docker Compose will use
docker compose config

# If override settings appear in the output, the merge is working
# If they don't appear, the override file isn't being loaded

Check the current directory:

pwd
ls docker-compose*.yml

# Must run docker compose from the directory containing both files
# Not from a parent or child directory

Fix 2: Understand Merge Behavior

Docker Compose merges files by overlaying the second file on top of the first. The merge rules differ by field type:

# docker-compose.yml
services:
  app:
    image: myapp:latest
    ports:
      - "3000:3000"
    environment:
      NODE_ENV: production
      API_URL: https://api.example.com
    volumes:
      - data:/app/data

# docker-compose.override.yml
services:
  app:
    ports:
      - "3001:3001"       # ADDS to ports (lists are appended, not replaced)
    environment:
      NODE_ENV: development  # REPLACES this key (mappings are merged by key)
      DEBUG: "true"          # ADDS new key
    volumes:
      - ./src:/app/src       # ADDS to volumes (lists are appended)

Merged result:

services:
  app:
    image: myapp:latest     # from base
    ports:
      - "3000:3000"         # from base
      - "3001:3001"         # from override (appended)
    environment:
      NODE_ENV: development  # override wins
      API_URL: https://api.example.com  # from base
      DEBUG: "true"          # from override
    volumes:
      - data:/app/data       # from base
      - ./src:/app/src       # from override (appended)

Key merge rules:

  • Mappings (objects): Merged by key — override values replace base values for matching keys, new keys are added
  • Sequences (lists): ports, volumes, environment arrays are appended — not replaced
  • Scalar values: Override replaces base

Fix 3: Explicit File Loading with -f

When you need to use -f, include both files explicitly:

# WRONG — only loads base file, override skipped
docker compose -f docker-compose.yml up

# CORRECT — load base + override explicitly
docker compose -f docker-compose.yml -f docker-compose.override.yml up

# Multiple overrides — applied left to right
docker compose \
  -f docker-compose.yml \
  -f docker-compose.override.yml \
  -f docker-compose.local.yml \
  up

Add a Makefile to avoid typing long commands:

# Makefile
dev:
	docker compose up

prod:
	docker compose -f docker-compose.yml -f docker-compose.prod.yml up

ci:
	docker compose -f docker-compose.yml -f docker-compose.ci.yml up --build

Fix 4: Environment-Specific Configuration Pattern

A common pattern uses a base file plus environment-specific overrides:

project/
├── docker-compose.yml           # Base: shared service definitions
├── docker-compose.override.yml  # Dev: auto-loaded, volume mounts, hot reload
├── docker-compose.prod.yml      # Prod: explicit -f required
├── docker-compose.ci.yml        # CI: explicit -f required
└── .env                         # Environment variables for all files
# docker-compose.yml — base (production-ready defaults)
services:
  app:
    image: myapp:${TAG:-latest}
    restart: unless-stopped
    environment:
      NODE_ENV: production
    networks:
      - backend

  db:
    image: postgres:16
    volumes:
      - pgdata:/var/lib/postgresql/data
    environment:
      POSTGRES_PASSWORD: ${DB_PASSWORD}
    networks:
      - backend

volumes:
  pgdata:

networks:
  backend:
# docker-compose.override.yml — development (auto-loaded)
services:
  app:
    build:
      context: .
      target: dev          # Use dev stage in multi-stage Dockerfile
    volumes:
      - ./src:/app/src     # Hot reload: mount source code
      - /app/node_modules  # Don't overwrite container's node_modules
    environment:
      NODE_ENV: development
      DEBUG: "app:*"
    ports:
      - "3000:3000"        # Expose port for local access
      - "9229:9229"        # Node.js debugger port

  db:
    ports:
      - "5432:5432"        # Expose DB for local tools (TablePlus, psql)
# docker-compose.prod.yml — production differences
# Usage: docker compose -f docker-compose.yml -f docker-compose.prod.yml up
services:
  app:
    image: registry.example.com/myapp:${TAG}
    deploy:
      replicas: 3
      resources:
        limits:
          memory: 512M

Fix 5: Override Specific Fields

Common patterns for overriding specific service properties:

# Override the build context (useful for CI vs local)
services:
  app:
    build:
      context: .
      dockerfile: Dockerfile.dev
      args:
        BUILD_ENV: development

# Override the command (run dev server instead of production server)
services:
  app:
    command: npm run dev
    # Base has: command: node dist/server.js

# Override the entrypoint
services:
  app:
    entrypoint: /bin/sh -c
    command: ["npm run dev"]

# Override health check
services:
  app:
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
      interval: 10s
      timeout: 5s
      retries: 3

Remove a value set in the base file — use null to unset:

# docker-compose.yml sets a restart policy
services:
  app:
    restart: unless-stopped

# docker-compose.override.yml removes it for development
services:
  app:
    restart: "no"   # Override to disable restart in dev

Fix 6: Debug Override Merging

When overrides aren’t applying as expected:

# See the fully merged configuration
docker compose config

# See only the config for one service
docker compose config app

# Validate syntax without running
docker compose config --quiet && echo "Config is valid"

# Check which files Docker Compose is reading
docker compose --verbose config 2>&1 | head -20
# Output includes: "Found project name: myproject"
# and lists the config files being merged

# Run with explicit debug output
COMPOSE_FILE=docker-compose.yml:docker-compose.override.yml docker compose config

Check environment variable substitution:

# .env file values are substituted in compose files
# Verify substitution is working:
docker compose config | grep -A5 "environment:"

# If variables show as empty, check .env file location
# .env must be in the same directory as docker-compose.yml

Fix 7: COMPOSE_FILE Environment Variable

Set override files permanently via environment variable instead of -f flags:

# Set in shell (current session)
export COMPOSE_FILE=docker-compose.yml:docker-compose.override.yml

# Set in .env file (persists for the project)
echo "COMPOSE_FILE=docker-compose.yml:docker-compose.override.yml" >> .env

# Now plain 'docker compose up' loads both files
docker compose up

Different separators by OS:

  • Linux/Mac: colon : separator
  • Windows: semicolon ; separator
# Windows
COMPOSE_FILE=docker-compose.yml;docker-compose.override.yml

Still Not Working?

Docker Compose v1 vs v2 differencesdocker-compose (v1) and docker compose (v2) handle some edge cases differently. If you’re using docker-compose (with hyphen), verify it’s finding the override file:

docker-compose --verbose config 2>&1 | grep -i "override\|reading"

Project name mismatch — if you run Docker Compose from different directories or with different project names, it may not recognize existing services. Use COMPOSE_PROJECT_NAME or the -p flag consistently.

Override file encoding — YAML is sensitive to indentation. A tab instead of spaces, or incorrect indentation level, causes the file to parse incorrectly (or silently fail to merge a section). Use docker compose config to confirm the merged output looks right.

For related Docker issues, see Fix: Docker Compose depends_on Not Working and Fix: Docker Compose Networking Not Working.

F

FixDevs

Solo developer based in Japan. Every solution is cross-referenced with official documentation and tested before publishing.

Was this article helpful?

Related Articles