Why queue mode matters
When you first install n8n it runs in single node mode. The editor and the execution engine share the same process. That’s fine for small flows, but once you start running heavy automations or high volumes of webhooks, the editor will feel sluggish.
Queue mode separates concerns. The editor stays responsive, jobs are pushed into Redis, and one or more workers pull them for execution. This model is how you scale n8n without losing stability.
How queue mode works under the hood
At the heart of queue mode are three moving parts:
- Editor process: Handles the UI, API, and scheduling. It writes jobs to Redis.
- Redis: Stores jobs temporarily. Think of it as the queue where workflows wait their turn.
- Workers: One or more worker processes pull jobs from Redis and run them. Each worker connects to the same PostgreSQL database.
The database remains the source of truth. Workflow definitions, credentials, and execution logs are all stored there. Redis only holds job metadata while jobs are waiting or running.
VPS requirements for queue mode
Queue mode needs more resources than single node, because you’re running at least three containers instead of two. At minimum:
- 2 vCPU / 4 GB RAM with NVMe storage for testing
- 4 vCPU / 8 GB RAM for real production with a few workers
- 8+ vCPU / 16+ GB RAM for higher concurrency or heavy tasks
Keep PostgreSQL on NVMe. Place the VPS near your APIs to reduce webhook latency.
Setting up queue mode with Docker Compose
Here’s a simple setup you can copy into your docker-compose.yml
:
version: "3.9"
services:
editor:
image: n8nio/n8n:latest
restart: unless-stopped
env_file: .env
command: n8n
depends_on:
- postgres
- redis
ports:
- "5678:5678"
volumes:
- n8n_data:/home/node/.n8n
worker:
image: n8nio/n8n:latest
restart: unless-stopped
env_file: .env
command: n8n worker
depends_on:
- postgres
- redis
volumes:
- n8n_data:/home/node/.n8n
redis:
image: redis:7-alpine
restart: unless-stopped
postgres:
image: postgres:16-alpine
restart: unless-stopped
environment:
POSTGRES_USER: n8n
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
POSTGRES_DB: n8n
volumes:
- pg_data:/var/lib/postgresql/data
volumes:
n8n_data:
pg_data:
In your .env
file add:
EXECUTIONS_MODE=queue
QUEUE_BULL_REDIS_HOST=redis
QUEUE_BULL_REDIS_PORT=6379
DB_TYPE=postgresdb
DB_POSTGRESDB_HOST=postgres
DB_POSTGRESDB_PORT=5432
DB_POSTGRESDB_DATABASE=n8n
DB_POSTGRESDB_USER=n8n
DB_POSTGRESDB_PASSWORD=<your_password>
Then bring it up:
docker compose up -d
Scale workers easily:
docker compose up -d --scale worker=3
Now three workers will process jobs in parallel.
Binary data and queue mode
This is where many tutorials get it wrong. By default n8n stores binary data in memory and keeps references in the database. That’s safe in queue mode. Do not try to share a filesystem mount for binary data between editor and workers — it’s not supported and leads to corruption. If you need persistent binaries, use an external storage adapter like S3 or MinIO.
Reverse proxy and public URLs
Queue mode still needs a reverse proxy. Make sure your proxy forwards these headers:
X-Forwarded-Proto
X-Forwarded-Host
X-Forwarded-For
In .env
set:
N8N_HOST=automation.example.com
N8N_PROTOCOL=https
WEBHOOK_URL=https://automation.example.com/
N8N_PROXY_HOPS=1
This ensures webhook URLs resolve correctly in the editor.
Monitoring queue mode
You need to keep an eye on:
- Queue depth: number of jobs waiting in Redis
- Execution time: how long workflows take to finish
- Worker health: are workers connected and pulling jobs
- Database load: Postgres connections and disk usage
- Redis latency: command timeouts or blocked clients
Prometheus and Grafana are common choices. For a quick check, Redis has redis-cli monitor
and n8n exposes metrics you can scrape.
When to scale workers
Add workers when:
- Queue depth keeps growing over time
- Execution times increase under load
- Webhooks start backing up
- CPU is consistently maxed out during jobs
Small, multiple workers are usually more effective than one big worker. They let you parallelize across CPUs and handle more bursts.
Common pitfalls in queue mode
- Credentials disappear: encryption key changed. Generate it once and keep it safe.
- Jobs hang forever: Redis not reachable or not enough workers.
- Webhook URLs wrong: proxy headers missing or
WEBHOOK_URL
not set. - Database bloat: old execution logs piling up. Use pruning settings.
Best practices for running queue mode in production
- Keep Postgres on its own volume and back it up nightly.
- Run Redis with persistence disabled unless you need durability.
- Use health checks to auto-restart stuck workers.
- Test restores and snapshots before major upgrades.
- Monitor early, not after users complain.
Closing thoughts
Queue mode is how you take n8n from a personal toy to a production automation system. It separates the editor from the heavy lifting, lets you scale horizontally, and keeps things stable under load. With Redis, Postgres, a couple of workers, and a clean VPS setup, you can run automations that would choke a single-node install.