← Blog

Autoalojar n8n en un servidor de 6 dólares

Railyard

1 de abril de 2026 · 11 min de lectura

Sigue esto en tu propio servidor. Empieza gratis, sin tarjeta

Toda herramienta de automatización de flujos de trabajo que cobra por ejecución convierte “conectar estas dos API” en un costo recurrente que crece exactamente con lo que automatizaste para dejar de pensar en eso. n8n hace el mismo trabajo que Zapier o Make, flujos visuales que llaman a API sin que tengas que escribir y mantener código de conexión, pero como software de código abierto que tú mismo alojas. Al final de esta guía tendrás tu propia instancia de n8n corriendo en un servidor de 6 USD al mes, accesible por HTTPS en tu propio dominio, respaldada por Postgres en lugar de un simple archivo SQLite, con copias de seguridad y una ruta de actualización que no te va a dejar en problemas.

Lo que necesitas

  • Un servidor. El Basic Droplet de DigitalOcean a 6,00 USD al mes da 1 vCPU, 1 GB de RAM y 25 GB de SSD, suficiente para correr n8n, Postgres y un proxy inverso juntos en una sola máquina, para uso personal o de un equipo pequeño. Cualquier servidor privado virtual con Ubuntu 24.04 de otro proveedor funciona igual.
  • Un nombre de dominio (o un subdominio de uno que ya tengas), con acceso a su configuración DNS.
  • Docker y el plugin de Docker Compose instalados en el servidor (se cubre en el paso 2).
  • Una terminal y acceso SSH al servidor.

Paso 1: crear el servidor y apuntar un dominio hacia él

Levanta un droplet con Ubuntu 24.04 en el plan Basic de 6 USD al mes de DigitalOcean (1 vCPU, 1 GB de RAM, 25 GB de SSD). Anota su dirección IP pública.

En la configuración DNS de tu dominio, agrega un registro A que apunte un subdominio, por ejemplo n8n.tudominio.com, hacia esa IP:

Type: A
Name: n8n
Value: <la IP de tu servidor>
TTL: 300

La propagación del DNS puede tardar desde minutos hasta algunas horas. Deberías ver que dig n8n.tudominio.com +short devuelve la IP de tu servidor antes de continuar, porque los pasos siguientes dependen de eso.

Paso 2: instalar Docker

Conéctate por SSH al servidor e instala Docker Engine junto con el plugin de Compose:

curl -fsSL https://get.docker.com | sh
sudo usermod -aG docker $USER

Cierra sesión y vuelve a entrar para que el cambio de grupo surta efecto, y luego confirma que ambas piezas están presentes:

docker --version
docker compose version

Deberías ver una versión de Docker y una versión de Compose impresas en pantalla, sin ningún error de “command not found”.

Paso 3: preparar la carpeta del proyecto y sus secretos

Crea una carpeta para la pila de servicios y un archivo .env para todo lo que no debería vivir en el propio archivo compose:

mkdir -p ~/n8n && cd ~/n8n

Genera una clave de cifrado real. n8n la usa para cifrar cada credencial guardada en su base de datos, así que perderla significa perder el acceso a todas las credenciales guardadas, no solo las de esta instalación:

openssl rand -base64 32

Crea .env con esa clave, tu dominio, una zona horaria y una contraseña de base de datos:

# .env
DOMAIN=n8n.tudominio.com
GENERIC_TIMEZONE=America/Mexico_City
N8N_ENCRYPTION_KEY=<pega la clave que acabas de generar>
POSTGRES_USER=n8n
POSTGRES_PASSWORD=<una contraseña larga y aleatoria>
POSTGRES_DB=n8n

Ajusta sus permisos para que solo tu usuario pueda leerlo:

chmod 600 .env

Paso 4: escribir el archivo de Docker Compose

n8n viene por defecto con una base de datos SQLite, lo cual está bien para probarlo, pero no para una instancia que corre todo el tiempo con más que un puñado de flujos de trabajo. Postgres es la base de datos que n8n mismo recomienda una vez superada la etapa de “solo estoy probando”, así que esta configuración la usa desde el principio.

Crea docker-compose.yml:

services:
  n8n:
    image: n8nio/n8n:1.68.0
    restart: unless-stopped
    environment:
      - N8N_HOST=${DOMAIN}
      - N8N_PROTOCOL=https
      - N8N_PORT=5678
      - N8N_WEBHOOK_URL=https://${DOMAIN}/
      - N8N_PROXY_HOPS=1
      - N8N_RUNNERS_ENABLED=true
      - N8N_ENCRYPTION_KEY=${N8N_ENCRYPTION_KEY}
      - GENERIC_TIMEZONE=${GENERIC_TIMEZONE}
      - DB_TYPE=postgresdb
      - DB_POSTGRESDB_HOST=postgres
      - DB_POSTGRESDB_PORT=5432
      - DB_POSTGRESDB_DATABASE=${POSTGRES_DB}
      - DB_POSTGRESDB_USER=${POSTGRES_USER}
      - DB_POSTGRESDB_PASSWORD=${POSTGRES_PASSWORD}
    volumes:
      - n8n_data:/home/node/.n8n
    depends_on:
      postgres:
        condition: service_healthy
    networks:
      - n8n-net

  postgres:
    image: postgres:16.4-alpine
    restart: unless-stopped
    environment:
      - POSTGRES_USER=${POSTGRES_USER}
      - POSTGRES_PASSWORD=${POSTGRES_PASSWORD}
      - POSTGRES_DB=${POSTGRES_DB}
    volumes:
      - postgres_data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB}"]
      interval: 5s
      timeout: 5s
      retries: 10
    networks:
      - n8n-net

  caddy:
    image: caddy:2
    restart: unless-stopped
    ports:
      - "80:80"
      - "443:443"
    environment:
      - DOMAIN=${DOMAIN}
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile
      - caddy_data:/data
      - caddy_config:/config
    depends_on:
      - n8n
    networks:
      - n8n-net

networks:
  n8n-net:

volumes:
  n8n_data:
  postgres_data:
  caddy_data:
  caddy_config:

Vale la pena explicar algunas decisiones:

  • La imagen de n8n queda fijada en 1.68.0 en lugar de latest. Una herramienta de automatización que se actualiza sola en silencio cuando el servidor se reinicia, arrastrando tus flujos de trabajo hacia lo que haya cambiado, no es un buen trato. Tú decides cuándo actualizar, eso se cubre en el paso 7.
  • N8N_PROXY_HOPS=1 y N8N_WEBHOOK_URL importan porque aquí n8n está detrás de Caddy en lugar de estar directamente expuesto a internet. Sin ellos, n8n no sabe cuál es su propia dirección HTTPS pública y registra las URL de webhook equivocadas con los servicios externos.
  • N8N_RUNNERS_ENABLED=true activa el task runner de n8n, que ejecuta los scripts de los nodos Code en un proceso aislado en lugar de dentro del proceso principal de n8n. Omitir esto en una versión 1.x significa que cualquier script en un nodo Code corre sin ningún aislamiento, lo cual importa en el momento en que corres flujos de trabajo que no escribiste tú mismo.
  • Solo Caddy publica puertos hacia el host. n8n y Postgres solo son accesibles en la red interna de Docker, no directamente desde internet.

Paso 5: escribir el Caddyfile y arrancar todo

Caddy gestiona automáticamente el certificado TLS de Let’s Encrypt, siempre que el DNS ya apunte hacia el servidor y los puertos 80 y 443 sean accesibles desde internet. Crea Caddyfile en la misma carpeta:

{$DOMAIN} {
	reverse_proxy n8n:5678
}

Arranca la pila de servicios:

docker compose up -d

Observa cómo arranca y confirma que Caddy efectivamente obtuvo un certificado:

docker compose logs -f caddy

Deberías ver una línea que mencione un certificado obtenido para tu dominio, y después, al visitar https://n8n.tudominio.com en un navegador, debería cargar la pantalla de configuración inicial de n8n con un candado válido, sin advertencia de certificado. Crea ahí tu cuenta de propietario; esa es la configuración de primer arranque del propio n8n, no algo que esta pila configure por ti.

Paso 6: respaldar flujos de trabajo, credenciales y la clave de cifrado

Hay tres cosas que hay que respaldar: la base de datos de Postgres (tus flujos de trabajo, ejecuciones y credenciales), el volumen n8n_data (el estado local propio de n8n, incluyendo todo lo que no está en la base de datos), y el archivo .env (tu clave de cifrado, sin la cual las credenciales de esa base de datos quedan ilegibles).

Un volcado diario de Postgres, guardado fuera del servidor:

docker compose exec -T postgres pg_dump -U n8n n8n > "n8n-backup-$(date +%F).sql"

Pon eso en una tarea cron y copia el resultado a algún lugar que no sea este droplet, un bucket de almacenamiento de objetos, otra máquina, cualquier sitio que no sea este servidor. Una copia de seguridad que vive únicamente en el servidor que respalda no sobrevive al tipo de falla que precisamente destruye un servidor.

Para el volumen y el archivo .env:

docker run --rm -v n8n_n8n_data:/data -v $(pwd):/backup alpine \
  tar czf /backup/n8n-data-backup.tar.gz -C /data .
cp .env ~/n8n-env-backup-$(date +%F)

Guarda esa copia de .env en un lugar aparte y con acceso controlado; contiene tanto la contraseña de tu base de datos como tu clave de cifrado.

Paso 7: actualizar n8n sin sorpresas

Revisa la versión que tienes corriendo actualmente, lee las notas de versión de n8n para todo lo que haya entre esa versión y la que vas a usar, y luego cambia la etiqueta en docker-compose.yml:

image: n8nio/n8n:1.69.0

Descarga y reinicia solo ese servicio:

docker compose pull n8n
docker compose up -d n8n

Deberías ver que los registros de n8n muestran un arranque limpio sin errores de migración de base de datos fallida, y tus flujos de trabajo existentes deberían seguir ahí cuando vuelvas a iniciar sesión. Si una migración falla, tu copia de seguridad de Postgres del paso 6 es el camino de vuelta a la versión anterior.

El atajo: hacerlo con Railyard

Todo lo anterior, un n8n respaldado por Postgres con una clave de cifrado generada automáticamente, un volumen de datos persistente y el HTTPS ya configurado, también existe como plantilla de un clic:

https://app.railyard.run/deploy?template=n8n

Esa plantilla de un solo contenedor es la opción correcta para el mismo caso que cubre la configuración manual de arriba: un usuario o un equipo pequeño que corre automatización interna. Si más adelante superas ese caso, con suficiente volumen de flujos de trabajo como para que la entrega de webhooks y la ejecución empiecen a competir por el mismo proceso, la propia arquitectura de n8n tiene un modo de cola que separa esas dos tareas, disponible como una plantilla de pila aparte: elige n8n (queue mode) en el catálogo de plantillas en lugar de desplegarla directamente desde un enlace, ya que una plantilla de pila requiere que confirmes antes sus servicios. Corre los procesos web y worker de n8n contra su propio Postgres y un Redis protegido con contraseña para la cola de trabajos.

Si prefieres empezar por conocer Railyard en general antes de decidirte por n8n en particular, la guía de inicio rápido cubre lo básico, y bases de datos y copias de seguridad explica cómo funcionan las copias de seguridad en todas las plantillas, no solo en esta. Botón de despliegue cubre el formato del enlace ?template= en sí, por si quieres incrustar uno en otro lugar. Para una comparación más amplia de lo que realmente te da un droplet de 6 USD frente a una alternativa administrada, consulta costos de alojamiento.

Solución de problemas

Caddy nunca obtiene un certificado, o el navegador muestra una advertencia de certificado. Esto casi siempre es cosa del DNS, no de Caddy. Corre dig n8n.tudominio.com +short desde tu propia máquina y confirma que devuelve la IP del servidor, no una IP vieja, y no nada. Let’s Encrypt también necesita que el puerto 80 sea accesible desde internet para la validación inicial, así que revisa que el firewall o el grupo de seguridad de tu proveedor de nube permita tráfico entrante en 80 y 443, no solo en 443.

docker compose up falla con “port is already allocated”. Algo más en la máquina ya está usando el puerto 80 o 443, comúnmente una instalación por defecto de Nginx o Apache. Encuéntralo con sudo ss -tlnp | grep -E ':80|:443' y detén ese servicio, o cambia los puertos que publica Caddy si de verdad necesitas tener ambos corriendo.

Los registros de n8n muestran URL de webhook que apuntan a la dirección equivocada, o a http en lugar de https. Revisa que N8N_HOST, N8N_PROTOCOL y N8N_WEBHOOK_URL en el archivo compose coincidan con tu dominio real y con https, y que N8N_PROXY_HOPS=1 esté configurado. Sin eso, n8n no confía en los encabezados reenviados que manda Caddy y termina adivinando su propia dirección.

El contenedor de Postgres sigue reiniciándose, o n8n no puede conectarse a la base de datos. Revisa primero docker compose logs postgres para ver el error real. Un POSTGRES_PASSWORD que no coincide con el DB_POSTGRESDB_PASSWORD que usa n8n para conectarse es la causa más común, generalmente por editar .env después de que el volumen de Postgres ya se inicializó con la contraseña anterior; Postgres solo lee esas variables de entorno en el primerísimo arranque, con un directorio de datos vacío.

El contenedor arranca y se cierra de inmediato, o el volumen muestra errores de permisos. Esto suele aparecer cuando montas una carpeta del host en lugar de un volumen de Docker con nombre para /home/node/.n8n. La imagen de n8n corre con un usuario que no es root, y una carpeta creada por root en el host no será escribible para ese usuario. Los volúmenes con nombre, como los del archivo compose de arriba, evitan esto por completo porque Docker administra su propiedad.

El servidor se queda sin memoria bajo carga real. Un droplet de 1 GB que corre n8n, Postgres y Caddy juntos tiene poco margen. Agrega un archivo swap como colchón (fallocate -l 2G /swapfile && chmod 600 /swapfile && mkswap /swapfile && swapon /swapfile), y si corres flujos de trabajo que procesan cargas grandes o muchas ejecuciones a la vez, sube a un droplet de 2 GB en lugar de depender del swap como solución permanente.

Preguntas frecuentes

¿Necesito Postgres, o basta con SQLite? SQLite, la opción por defecto de n8n, funciona para probarlo, pero no maneja bien más que un puñado de flujos de trabajo simultáneos y no es lo que n8n recomienda una vez que una instancia realmente se usa en serio. Empezar con Postgres desde el inicio, como en esta guía, evita una migración más adelante.

¿Puedo hacer esto sin un dominio, solo con la IP del servidor? El HTTPS automático de Caddy necesita un nombre de dominio real; Let’s Encrypt no emite certificados para direcciones IP sueltas. Puedes correrlo sobre HTTP simple en una IP para una prueba rápida apuntando un navegador directo al puerto 5678, pero no guardes credenciales reales en una instancia que no esté detrás de HTTPS.

¿Cuánto cuesta realmente correr esto? El servidor cuesta 6 USD al mes. n8n en sí es software de código abierto gratuito, sin límites de ejecución propios; pagas por la máquina donde corre, no por lo que corre en ella.

¿Qué pasa con mis flujos de trabajo si pierdo la clave de cifrado? Cada credencial que n8n tenía guardada se vuelve ilegible. La estructura de los flujos de trabajo sobrevive, pero todo lo que necesitaba una clave de API o un token OAuth guardado tendrá que recibir esas credenciales de nuevo. Esta es exactamente la razón por la que el paso 6 respalda .env por separado de la base de datos.

¿La configuración de un solo contenedor de aquí es la misma que corre la plantilla de n8n de Railyard? Casi, con una diferencia real: la plantilla de Railyard no incluye Postgres por defecto, porque la mayoría de las instalaciones de un solo usuario no la necesitan desde el primer día. La arquitectura, un contenedor de n8n con una clave de cifrado generada y un volumen de datos persistente, es la misma idea; esta guía agrega Postgres porque es la opción por defecto más honesta para cualquier cosa que pienses mantener corriendo.

Cualquiera de los dos caminos te lleva al mismo lugar al final: tu propio servidor de automatización, tus propios datos, y una factura que no se mueve cuando tus flujos de trabajo hacen más trabajo.

Por qué eligen Railyard para esto

  • Tu propia cuenta en la nube. Despliega en DigitalOcean, Hetzner, Vultr, AWS, OVHcloud, o cualquier servidor Linux por SSH, facturado directamente por tu proveedor, sin márgenes adicionales.
  • Un precio fijo por equipo. El plan Free es gratis para siempre: un servidor más un servidor de base de datos, tres apps, sin tarjeta. Pro cuesta $19 al mes por hasta cinco servidores y apps ilimitadas. Team cuesta $49 al mes con servidores ilimitados. Sin cargos por app, por despliegue, por asiento ni por gigabyte.
  • Plantillas de un clic. Despliega apps de código abierto, como bases de datos, analítica y herramientas de desarrollo, en tu propio servidor con un clic.
  • Bases de datos administradas. Postgres, MySQL y Redis, con copias de seguridad programadas y verificadas por restauración, y recuperación a un punto en el tiempo.
  • Despliegue con git push. Despliega desde GitHub, GitLab o la CLI, con HTTPS automático y lanzamientos sin tiempo de inactividad.

Sáltate la configuración del servidor

Despliega la plantilla verificada de n8n en Railyard con un clic y obtén una instancia funcionando con HTTPS ya configurado.

Plan gratis, sin tarjeta, y 14 días de Pro para cada equipo nuevo. Un precio fijo por equipo.