TL;DR
Docker can't mount a directory that doesn't exist yet. Create it first, then re-run your container:
mkdir -p /path/to/your/host/directory
docker run -v /path/to/your/host/directory:/container/path your-image
For Docker Compose, either create the folder manually before running docker compose up, or switch to a named volume and let Docker handle it.
What Triggers This Error
The full error reads:
Error response from daemon: invalid mount config for type "bind": bind source path does not exist
Bind mounts work by linking a host directory directly into the container filesystem. Docker doesn't create that directory for you โ it must already exist. Named volumes are different; Docker manages those automatically. Bind mounts? You're responsible for the source path.
Common culprits:
- Typo in the host path (e.g.,
/dat/myappinstead of/data/myapp) - Path is relative to the wrong working directory
- Directory was deleted or never created in the first place
- On Windows/WSL2: mixing Windows and Unix path formats
- Docker Compose
volumesblock points to a host path that doesn't exist
Fix 1: Create the Missing Host Directory
Nine times out of ten, this is all you need. Find the path in your -v flag and create it:
# Your failing command
docker run -v /data/myapp/config:/app/config myimage
# Create the missing directory
mkdir -p /data/myapp/config
# Run again โ should work now
docker run -v /data/myapp/config:/app/config myimage
The -p flag tells mkdir to create all parent directories in one shot. No need to create /data then /data/myapp separately.
Fix 2: Check for Typos First
Worth doing before you create anything new โ the path might already exist, just misspelled:
# Does it exist?
ls -la /data/myapp/config
# One-liner check
[ -d /data/myapp/config ] && echo "exists" || echo "missing"
One wrong character is enough. /data/myapp and /dat/myapp are completely different paths. Check every segment.
Fix 3: Docker Compose โ Relative Paths and Named Volumes
This catches a lot of people. Take this docker-compose.yml:
services:
app:
image: myimage
volumes:
- ./config:/app/config
That ./config resolves relative to wherever your docker-compose.yml lives. If the config folder isn't there, Docker bails immediately. The fix is simple:
# Run this from the same directory as docker-compose.yml
mkdir -p config
docker compose up -d
Don't actually need files in that directory beforehand? Switch to a named volume instead:
services:
app:
image: myimage
volumes:
- app-config:/app/config
volumes:
app-config:
Docker creates named volumes automatically on first run. Use bind mounts when you need to read or write files directly from the host โ config files, build artifacts, logs you want to tail in real time.
Fix 4: Windows and WSL2 Path Formats
Docker Desktop on Windows is picky about path format. Use the wrong style for your terminal and you'll get this error every time.
From PowerShell or CMD:
# Wrong โ Unix-style path won't resolve
docker run -v /c/Users/you/data:/app/data myimage
# Correct โ Windows backslashes
docker run -v C:\Users\you\data:/app/data myimage
# Also correct โ forward slashes work too
docker run -v C:/Users/you/data:/app/data myimage
From a WSL2 terminal, stick to Linux paths:
# Native WSL2 path
docker run -v /home/you/data:/app/data myimage
# Accessing your Windows C: drive from WSL
docker run -v /mnt/c/Users/you/data:/app/data myimage
The rule: match the path style to the shell you're running from.
Fix 5: Empty Environment Variables
Variables that look set but aren't will silently produce a broken path:
# If $DATA_DIR is unset, this becomes -v :/app/data โ instant error
docker run -v $DATA_DIR:/app/data myimage
# Debug first
echo "DATA_DIR=${DATA_DIR}"
# Add a fallback so it never expands to nothing
docker run -v ${DATA_DIR:-/tmp/myapp-data}:/app/data myimage
An unset variable expands to an empty string. Docker sees -v :/app/data, which points nowhere.
Verify the Fix
Container running? Double-check the mount actually landed correctly:
# Start a named container
docker run -d --name test-bind -v /data/myapp/config:/app/config myimage
# Confirm it's up
docker ps | grep test-bind
# Inspect the mount details
docker inspect test-bind --format '{{ json .Mounts }}' | python3 -m json.tool
Look for "Type": "bind" in the output, with your expected source and destination paths. If those are correct, you're done.
For Compose stacks:
docker compose up -d
docker compose ps
docker compose exec app ls /app/config
Quick Reference
- Named volume โ Docker creates and manages it; no host path required
- Bind mount โ Host path must exist before the container starts
- tmpfs mount โ Lives in memory only; gone when the container stops
Running this in CI/CD? Add a directory setup step before your Docker commands:
mkdir -p ./data ./logs ./config
docker compose up -d
Three seconds of prep, zero bind mount errors.

