How to Self-Host n8n (Workflow Automation) on a VPS
A self-hosted Zapier alternative with no per-task fees. Install n8n on a VPS with Docker and HTTPS and automate anything with hundreds of integrations.

n8n is a fair-code workflow automation tool — think Zapier or Make, but running on your own server with no per-execution billing and full access to your data. Self-hosting also unlocks unlimited workflows and executions. This guide installs it with Docker and HTTPS so webhooks work reliably. Budget 20 minutes.
Why self-host n8n?
- No per-task fees: run thousands of executions without a growing bill.
- Data stays yours: sensitive credentials and payloads never touch a third party.
- Webhook-friendly: a public HTTPS URL means services can call your workflows directly.
Prerequisites
- A VPS with at least 2 GB RAM and Docker installed — run Docker on a VPS.
- A domain with an A record, e.g.
n8n.example.com. HTTPS matters here because many integrations require secure webhook URLs.
Deploy n8n with Compose
We'll pair n8n with Caddy for automatic TLS and Postgres for durable storage.
mkdir -p ~/n8n && cd ~/n8n
services:
db:
image: postgres:16
restart: unless-stopped
environment:
- POSTGRES_USER=n8n
- POSTGRES_PASSWORD=change-me
- POSTGRES_DB=n8n
volumes:
- db:/var/lib/postgresql/data
n8n:
image: n8nio/n8n:latest
restart: unless-stopped
depends_on:
- db
environment:
- DB_TYPE=postgresdb
- DB_POSTGRESDB_HOST=db
- DB_POSTGRESDB_USER=n8n
- DB_POSTGRESDB_PASSWORD=change-me
- N8N_HOST=n8n.example.com
- N8N_PROTOCOL=https
- WEBHOOK_URL=https://n8n.example.com/
- GENERIC_TIMEZONE=Europe/London
volumes:
- n8n:/home/node/.n8n
caddy:
image: caddy:2
restart: unless-stopped
ports:
- "80:80"
- "443:443"
volumes:
- ./Caddyfile:/etc/caddy/Caddyfile
- caddy_data:/data
depends_on:
- n8n
volumes:
db:
n8n:
caddy_data:
Caddyfile:
n8n.example.com {
reverse_proxy n8n:5678
}
docker compose up -d
Open https://n8n.example.com, create the owner account, and you're in the editor.

Build your first workflow
n8n is node-based: you chain a trigger to actions. A classic first workflow:
- Trigger: a Webhook node — n8n gives you a URL to call.
- Action: an HTTP Request or an app node (Gmail, Slack, a database).
- Logic: IF/Switch nodes to branch on the data.
Click Execute Workflow to test, then toggle it Active so it runs on its own.
Keep webhooks and credentials safe
- Only open 80/443/SSH on the firewall.
- Store secrets in n8n's Credentials vault, never hard-coded in nodes.
- Set
N8N_ENCRYPTION_KEY(via an env var) so credentials are encrypted at rest, and back up then8nvolume — it holds your workflows and keys.
Keep it updated
cd ~/n8n
docker compose pull && docker compose up -d
Workflow ideas to get you started
The fastest way to learn n8n is to automate something real. A few practical starters:
- Form → spreadsheet → Slack: a webhook receives a form submission, appends a row to a Google Sheet, and posts a summary to Slack.
- RSS → social: poll a feed and auto-post new items — pairs well with a self-hosted FreshRSS feed.
- Backup watchdog: on a schedule, check that a file exists or an API is healthy, and email you if it isn't.
- Inbox routing: parse incoming emails and create tasks or tickets automatically.
Use the IF, Switch and Merge nodes for logic, and the Code node when you need a few lines of JavaScript no built-in node covers.
Scaling and reliability
For light use the single-container setup here is plenty. As workflows multiply, two settings matter: turn on execution pruning (via EXECUTIONS_DATA_PRUNE) so old run data doesn't bloat Postgres, and for heavy webhook volume consider n8n's queue mode, which runs separate worker processes backed by Redis. Always keep the n8n data volume and the Postgres database in your backups — together they hold your workflows and encrypted credentials.
Credentials, encryption and security
n8n stores the API keys, OAuth tokens and passwords your workflows use in its Credentials vault, encrypted at rest. Two settings make this robust:
- Set
N8N_ENCRYPTION_KEYto a strong, fixed value via an environment variable. If you don't, n8n generates one on first run and stores it in the data volume — losing it makes every saved credential unreadable, so set it explicitly and keep a copy safe. - Restrict access. Keep only 80/443/SSH open, enable n8n's user management so the editor requires a login, and never expose the raw
5678port to the internet — the reverse proxy is the only thing that should reach it.
For OAuth integrations (Google, Slack and friends) the callback URL must be your HTTPS domain, which is another reason the TLS setup earlier matters. Treat your n8n instance like any other credential store: patched, backed up and behind a login, because a compromised automation server is a compromised key to every service it connects to.
FAQ
Is self-hosted n8n free?
The community edition is free to self-host under a fair-code licence. You only pay for the VPS. Some enterprise features are separate, but the core automation engine is fully usable.
n8n vs Zapier — what's the catch?
n8n has a steeper learning curve and you maintain the server, but there are no per-task fees and your data stays private. For high-volume automations it's dramatically cheaper.
Why does n8n need HTTPS?
Many services will only send webhooks to secure URLs, and OAuth callbacks generally require HTTPS. Running behind Caddy or Nginx with a valid certificate avoids integration failures.
How much RAM does n8n use?
A light instance runs in around 512 MB–1 GB, but complex workflows and Postgres push that up. 2 GB is a comfortable starting point.
Automate everything on your own terms. Deploy on purpose-built n8n hosting with one-click setup, or browse VPS plans to size it yourself.