How to Pass Environment Variables to Docker Compose
In this tutorial, you'll learn about How to Pass Environment Variables to Docker Compose. We cover key concepts, practical examples, and best practices.
The Problem
Your Docker container cannot connect to the database because DB_HOST or DB_PASSWORD is not set. You need to pass environment variables to containers defined in docker-compose.yml without hardcoding secrets.
Quick Fix
Step 1: Set variables with the environment key
Add inline environment variables to a service:
services:
app:
image: my-app:latest
environment:
- DB_HOST=postgres
- DB_PORT=5432
- DEBUG=true
Step 2: Use an env_file
Store variables in a file and reference it:
echo "DB_HOST=postgres" > db.env
echo "DB_PORT=5432" >> db.env
echo "DB_PASSWORD=secret123" >> db.env
services:
app:
image: my-app:latest
env_file:
- db.env
Step 3: Use a .env file for variable substitution
Docker Compose reads .env from the project directory automatically:
echo "DB_HOST=postgres" > .env
echo "APP_PORT=8080" >> .env
Reference variables in docker-compose.yml:
services:
app:
image: my-app:latest
environment:
- DB_HOST=${DB_HOST}
ports:
- "${APP_PORT}:3000"
Step 4: Pass variables from the shell at runtime
Override variables when running <a href="/devops/docker-compose/">docker compose</a> up:
DB_HOST=staging-db docker compose up -d
Step 5: Use secrets for sensitive data
For production, use Docker secrets:
services:
app:
image: my-app:latest
secrets:
- db_password
secrets:
db_password:
file: ./secrets/db_password.txt
Alternative Solutions
Use variable substitution with defaults
Provide fallback values for undefined variables:
environment:
- DB_HOST=${DB_HOST:-localhost}
- DB_PORT=${DB_PORT:-5432}
Pass host machine environment variables
Forward variables from the host to the container:
environment:
- HOSTNAME
- USERNAME
Common Mistakes to Avoid
Hardcoding secrets in docker-compose.yml. The compose file is often committed to version control. Use .env or Docker secrets for sensitive values.
Not escaping special characters in .env files. Values with spaces, $, or # must be quoted or escaped. Use single quotes around values with special characters.
Overriding variables unintentionally. Shell variables override .env values. Be aware of what is set in your shell environment.
Pro Tips
Use multiple .env files with env_file. Add several env files with different precedence: env_file: [.env.common, .env.local] where later files override earlier ones.
Use docker compose config to resolve variables. See the final resolved configuration with all variables substituted: <a href="/devops/docker-compose/">docker compose</a> config.
Use shell variables with higher precedence. Shell-level variables override .env file values, useful for CI overrides: DB_HOST=staging <a href="/devops/docker-compose/">docker compose</a> up -d.
Use environment-specific .env files. Create .env.dev, .env.staging, and .env.prod files and reference them conditionally: <a href="/devops/docker-compose/">docker compose</a> --env-file .env.prod up -d.
Use docker compose config to see resolved environment values. Run <a href="/devops/docker-compose/">docker compose</a> config after defining environment variables to verify they are set correctly before starting services.
Use the env_file directive to share common variables across services. Instead of duplicating same variables in multiple services, define them in a shared .env file and reference it from each service.
Prevention
- Use
.envfor non-sensitive configuration that varies per environment. - Use
env_filefor larger sets of related variables. - Never commit
.envor secrets files to version control.
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro