Tips > Ops & Security

Use a `.env` File for Docker Compose Configuration

Hardcoding database passwords, hostnames, and feature flags directly in `docker-compose.yml` makes the file non-portable and creates security risks when the ...

Hardcoding database passwords, hostnames, and feature flags directly in docker-compose.yml makes the file non-portable and creates security risks when the Compose file is committed to version control. Docker Compose natively reads a .env file in the same directory, allowing you to separate configuration from infrastructure definition.

Real-world example: You maintain a single docker-compose.yml that works across development, staging, and production by swapping only the .env file.


# n8n Configuration

N8N_VERSION=1.94.1
N8N_HOST=n8n.example.com
N8N_PROTOCOL=https
GENERIC_TIMEZONE=America/New_York

# Database

POSTGRES_DB=n8n_db
POSTGRES_USER=n8n_user
POSTGRES_PASSWORD=a-strong-random-password-here
POSTGRES_VERSION=16

# Execution Settings

EXECUTIONS_DATA_PRUNE=true
EXECUTIONS_DATA_MAX_AGE=168

# Encryption key for credentials (generate once, never change)

N8N_ENCRYPTION_KEY=your-generated-encryption-key
```text
```yaml title="docker-compose.yml"
services:
  postgres:
    image: postgres:${POSTGRES_VERSION}-alpine
    environment:
      POSTGRES_DB: ${POSTGRES_DB}
      POSTGRES_USER: ${POSTGRES_USER}
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}

  n8n:
    image: n8nio/n8n:${N8N_VERSION}
    environment:
      DB_TYPE: postgresdb
      DB_POSTGRESDB_HOST: postgres
      DB_POSTGRESDB_DATABASE: ${POSTGRES_DB}
      DB_POSTGRESDB_USER: ${POSTGRES_USER}
      DB_POSTGRESDB_PASSWORD: ${POSTGRES_PASSWORD}
      N8N_HOST: ${N8N_HOST}
      N8N_PROTOCOL: ${N8N_PROTOCOL}
      GENERIC_TIMEZONE: ${GENERIC_TIMEZONE}
      EXECUTIONS_DATA_PRUNE: ${EXECUTIONS_DATA_PRUNE}
      EXECUTIONS_DATA_MAX_AGE: ${EXECUTIONS_DATA_MAX_AGE}
      N8N_ENCRYPTION_KEY: ${N8N_ENCRYPTION_KEY}
```text
```bash title=".gitignore"

# Never commit secrets

.env
```text
> **Danger: The Encryption Key**
>
> `N8N_ENCRYPTION_KEY` encrypts all stored credentials. If you lose this key, every credential in n8n becomes unreadable and must be re-entered. Generate it once with `openssl rand -hex 32`, store it in your `.env` file, and back it up separately from the database.

This pattern keeps secrets out of version control, makes environment promotion straightforward, and lets you generate environment-specific configs from a template.

**Related:** [Set a Unique Encryption Key and Back It Up](../security-best-practices/01-set-a-unique-encryption-key-and-back-it-up.md) | [Configure Payload Size and Binary Data Mode for Large Files](../performance-and-large-files/01-configure-payload-size-and-binary-data-mode-for-large-files.md)

Showcase builds

19 complete workflows from my own projects, each with its n8n workflow JSON to import. Showcase entries link the file at the end of the article.

See the showcase builds

Keep reading

191 entries grouped by topic, from first workflow to queue mode. Free, no signup.

Browse the encyclopedia

Need it built?

I design, build and run n8n systems for clients. Every engagement starts with a $1,500 diagnostic audit, credited toward the build.

Book a 20-minute call