Install n8n on Docker with a single docker run command for quick testing, or use Docker Compose for production with persistent data, environment variables, and automatic restarts. Mount a volume for the .n8n directory to persist workflows and credentials across container restarts. Set N8N_ENCRYPTION_KEY to protect stored credentials.
Running n8n with Docker
Docker is the recommended way to run n8n in production. It provides a consistent environment, easy updates, and simple deployment. You can start with a single docker run command for testing, then move to Docker Compose when you need persistent data, environment variables, and integration with other services like PostgreSQL and Redis. This tutorial covers both approaches, from quick start to production-ready configuration.
Prerequisites
- Docker installed on your system (Docker Desktop for macOS/Windows, or Docker Engine for Linux)
- Docker Compose v2 (included with Docker Desktop, or install separately on Linux)
- Basic familiarity with the command line
- Port 5678 available on the host machine
Step-by-step guide
Run n8n with a quick-start Docker command
Run n8n with a quick-start Docker command
The fastest way to try n8n is a single docker run command. This pulls the official n8n image and starts the container with port 5678 exposed. The --rm flag removes the container when you stop it, and -it enables interactive mode so you can see the logs. This setup is for testing only — data is lost when the container stops.
1docker run -it --rm \2 --name n8n \3 -p 5678:5678 \4 docker.n8n.io/n8nio/n8nExpected result: n8n starts and the editor is accessible at http://localhost:5678 in your browser.
Add a persistent volume for data storage
Add a persistent volume for data storage
To keep your workflows, credentials, and execution data across container restarts, mount a Docker volume to /home/node/.n8n inside the container. This directory contains n8n's SQLite database, encryption keys, and configuration. Use a named volume for Docker-managed storage, or a bind mount for a specific directory on the host.
1docker run -d \2 --name n8n \3 --restart always \4 -p 5678:5678 \5 -v n8n_data:/home/node/.n8n \6 docker.n8n.io/n8nio/n8nExpected result: n8n starts in the background with persistent storage. Workflows and credentials survive container restarts.
Set essential environment variables
Set essential environment variables
Configure n8n with environment variables using the -e flag. At minimum, set N8N_ENCRYPTION_KEY to a random 32-character hex string. This key encrypts stored credentials. Without it, n8n generates a random key on first start, but if the key is lost (e.g., the container is recreated without the volume), credentials become unreadable. Also set WEBHOOK_URL if n8n is behind a reverse proxy.
1# Generate an encryption key2openssl rand -hex 3234# Run n8n with environment variables5docker run -d \6 --name n8n \7 --restart always \8 -p 5678:5678 \9 -v n8n_data:/home/node/.n8n \10 -e N8N_ENCRYPTION_KEY=your_generated_key_here \11 -e WEBHOOK_URL=https://n8n.yourdomain.com \12 -e GENERIC_TIMEZONE=America/New_York \13 -e TZ=America/New_York \14 docker.n8n.io/n8nio/n8nExpected result: n8n starts with a fixed encryption key and correct timezone. Credentials are encrypted and recoverable.
Create a Docker Compose file for production
Create a Docker Compose file for production
For production deployments, use a docker-compose.yml file to define your n8n service along with any dependencies. Docker Compose makes it easy to manage environment variables, volumes, networking, and multi-service setups. Create a docker-compose.yml file in your project directory with the n8n service definition.
1version: '3.8'23services:4 n8n:5 image: docker.n8n.io/n8nio/n8n6 restart: always7 ports:8 - '5678:5678'9 environment:10 - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}11 - WEBHOOK_URL=${WEBHOOK_URL:-http://localhost:5678}12 - GENERIC_TIMEZONE=${TIMEZONE:-UTC}13 - TZ=${TIMEZONE:-UTC}14 - N8N_PORT=567815 volumes:16 - n8n_data:/home/node/.n8n1718volumes:19 n8n_data:Expected result: Running docker compose up -d starts n8n with all configuration defined in the Compose file.
Start n8n with Docker Compose
Start n8n with Docker Compose
Navigate to the directory containing your docker-compose.yml file. Create a .env file with your secrets. Then run docker compose up -d to start n8n in the background. Use docker compose logs -f n8n to follow the logs and verify n8n starts successfully.
1# Create .env file2echo 'N8N_ENCRYPTION_KEY=your_generated_key_here' > .env3echo 'WEBHOOK_URL=https://n8n.yourdomain.com' >> .env4echo 'TIMEZONE=America/New_York' >> .env56# Start n8n7docker compose up -d89# Check logs10docker compose logs -f n8nExpected result: n8n starts in the background. The logs show 'n8n ready on port 5678' and the editor is accessible.
Update n8n to the latest version
Update n8n to the latest version
To update n8n, pull the latest image and recreate the container. Docker Compose makes this simple with two commands. Your data is preserved in the named volume. Always back up your data before updating, especially across major version changes.
1# With Docker Compose2docker compose pull3docker compose up -d45# With plain Docker6docker stop n8n7docker rm n8n8docker pull docker.n8n.io/n8nio/n8n9docker run -d --name n8n --restart always \10 -p 5678:5678 \11 -v n8n_data:/home/node/.n8n \12 -e N8N_ENCRYPTION_KEY=your_key \13 docker.n8n.io/n8nio/n8nExpected result: n8n restarts with the latest version. Existing workflows and credentials are preserved.
Complete working example
1version: '3.8'23# Production-ready n8n Docker Compose configuration4# Usage:5# 1. Create a .env file with N8N_ENCRYPTION_KEY and WEBHOOK_URL6# 2. Run: docker compose up -d7# 3. Access: http://localhost:567889services:10 n8n:11 image: docker.n8n.io/n8nio/n8n12 restart: always13 ports:14 - '5678:5678'15 environment:16 # Required: encryption key for stored credentials17 - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}18 # Required if behind reverse proxy19 - WEBHOOK_URL=${WEBHOOK_URL:-http://localhost:5678}20 # Timezone21 - GENERIC_TIMEZONE=${TIMEZONE:-UTC}22 - TZ=${TIMEZONE:-UTC}23 # Port (default 5678)24 - N8N_PORT=567825 # Execution data pruning26 - EXECUTIONS_DATA_PRUNE=true27 - EXECUTIONS_DATA_MAX_AGE=16828 # Disable telemetry (optional)29 # - N8N_DIAGNOSTICS_ENABLED=false30 volumes:31 - n8n_data:/home/node/.n8n32 healthcheck:33 test: ['CMD-SHELL', 'wget -qO- http://localhost:5678/healthz || exit 1']34 interval: 30s35 timeout: 10s36 retries: 337 start_period: 30s3839volumes:40 n8n_data:Common mistakes when installing n8n on Docker
Why it's a problem: Running n8n without a persistent volume, losing all data on container restart
How to avoid: Always mount a volume to /home/node/.n8n: -v n8n_data:/home/node/.n8n
Why it's a problem: Not setting N8N_ENCRYPTION_KEY, then losing credentials when the container is recreated
How to avoid: Generate a key with openssl rand -hex 32 and pass it as an environment variable on every run.
Why it's a problem: Using the latest tag in production, causing unexpected breaking changes after docker pull
How to avoid: Pin to a specific version tag like docker.n8n.io/n8nio/n8n:1.30.0.
Why it's a problem: Exposing port 5678 to the public internet without authentication
How to avoid: Put n8n behind a reverse proxy (Nginx, Caddy, Traefik) with HTTPS and set up n8n's built-in basic authentication.
Best practices
- Always set N8N_ENCRYPTION_KEY explicitly and store it securely — losing it makes credentials unrecoverable
- Use named Docker volumes instead of bind mounts for cleaner management
- Set --restart always so n8n recovers from host reboots automatically
- Pin to a specific image tag in production (e.g., n8n:1.30.0) to avoid unexpected breaking changes
- Use a .env file for secrets instead of hardcoding them in docker-compose.yml
- Set EXECUTIONS_DATA_PRUNE=true and EXECUTIONS_DATA_MAX_AGE=168 to prevent disk space issues
- Add a health check so Docker can detect and restart unhealthy containers
- Back up the n8n_data volume before major version updates
Still stuck?
Copy one of these prompts to get a personalized, step-by-step explanation.
How do I install and run n8n using Docker with persistent data storage? I need both a quick docker run command for testing and a Docker Compose setup for production.
Create a docker-compose.yml for n8n with a persistent volume, encryption key, webhook URL, timezone, execution data pruning, and a health check. Include a .env file template.
Frequently asked questions
What is the official Docker image for n8n?
The official image is docker.n8n.io/n8nio/n8n. Pull it with docker pull docker.n8n.io/n8nio/n8n. Do not use unofficial images from Docker Hub.
Can I run n8n on Docker Desktop for macOS or Windows?
Yes. Docker Desktop works on macOS and Windows. The same docker run and docker compose commands work on all platforms.
How do I access the n8n editor after starting the container?
Open http://localhost:5678 in your browser. If you changed the port with N8N_PORT or -p, use that port instead.
How much memory does n8n need in Docker?
n8n works with 256 MB minimum for light workloads. For production with multiple concurrent workflows, allocate 1-2 GB. Monitor memory usage with docker stats.
Can I run multiple n8n containers on the same host?
Yes. Use different ports (-p 5679:5678) and different volume names for each instance. For scaling, consider queue mode instead of running independent instances.
Can RapidDev help deploy n8n on Docker in production?
Yes. RapidDev can set up a production n8n deployment on Docker with PostgreSQL, Redis, reverse proxy, SSL, monitoring, and automated backups.
Talk to an Expert
Our team has built 600+ apps. Get personalized help with your project.
Book a free consultation