Skip to main content

Headscale + Headplane (GUI): Tu propio servidor Tailscale autohospedado


Introducción

Este artículo documenta el despliegue de Headscale como servidor de control autohospedado para redes tipo Tailscale, junto con Headplane como interfaz gráfica de administración.

Headscale es una implementación open‑source del backend de Tailscale que permite operar una red VPN en malla basada en WireGuard sin depender de servicios externos. Todo el control —usuarios, nodos, claves, políticas y DNS— reside en infraestructura propia.

El modelo de red es mesh: los dispositivos intentan comunicarse directamente entre sí, recurriendo a un relay (DERP) únicamente cuando no es posible establecer conexión directa. Esto reduce latencia, evita tráfico innecesario y mantiene el control del plano de datos.

Headplane complementa a Headscale aportando una GUI web moderna para la gestión diaria: visualización de nodos, usuarios, ACLs, DNS, políticas y estado general del tailnet. No sustituye al CLI de Headscale, pero reduce fricción operativa y errores humanos.


Configuración con Docker

El despliegue se realiza íntegramente mediante contenedores. El archivo docker-compose.yml, junto con el resto de configuraciones asociadas, se mantiene versionado en Gitea:

docker-compose.yml en Gitea

La separación entre servicios permite actualizar Headscale o Headplane de forma independiente y facilita la trazabilidad de cambios.


Estructura de directorios esperada

La estructura del directorio está pensada para aislar configuraciones y datos persistentes, evitando mezclas entre componentes:

.
├── data
│   └── ...
├── docker-compose.yml
├── Headplane
│   └── config.yaml
└── Headscale
    ├── acl.hujson
    └── config.yaml

Los volúmenes se montan utilizando el UID/GID del usuario normal del sistema (1000:1000), simplificando permisos y evitando dependencias de root dentro de los contenedores.


Configuración de Headplane

La configuración de Headplane se gestiona mediante su propio archivo config.yaml, disponible en el repositorio:

config.yaml de Hadplane en Gitea

Headplane actúa como capa de presentación y orquestación visual sobre la API de Headscale. Para ello requiere una API Key válida, que se genera desde el propio Headscale.

La interfaz web de Headplane puede protegerse sin problema tras un proxy con autenticación (por ejemplo, Authentik), añadiendo control de acceso sin interferir con el funcionamiento interno de Headscale.


Configuración de Headscale

El archivo principal de configuración de Headscale define el comportamiento global del servidor: URLs, DNS, política, DERP, almacenamiento y autenticación.

Config disponible en:

config.yaml de Headscale en Gitea

Las ACLs se mantienen separadas en acl.hujson, permitiendo versionarlas y modificarlas sin tocar el núcleo de configuración.


Pasos iniciales

Una vez definida la estructura y las configuraciones:

  1. Levantar el stack de contenedores:
docker-compose up -d
  1. Generar una API Key para consumo externo (Headplane u otros clientes):
docker exec Headscale headscale apikeys create
  1. Añadir la API Key generada al docker-compose.yml (servicio Headplane) y reiniciar los contenedores:
docker-compose restart
  1. Acceder a la interfaz web de Headplane:
http://<IP_DEL_SERVIDOR>:3170
  1. Crear el primer usuario en Headscale:
docker exec Headscale headscale users create <nombre>

A partir de este punto, los nodos pueden empezar a autenticarse y unirse al tailnet.


Consideraciones importantes (Headscale 0.26+)

Desde la versión 0.26, Headscale introduce cambios relevantes que afectan a despliegues existentes y nuevos:

  • Los identificadores de usuario deben incluir @ (por ejemplo, usuario@dominio).
  • base_domain no puede coincidir con server_url.
  • Las ACLs clásicas quedan obsoletas: es obligatorio migrar a Policy v2.

La migración y los cambios asociados se documentan en:

Consideraciones tras la actualización a la v0.26

Ignorar estos puntos suele derivar en errores de autenticación, problemas de registro de nodos o políticas que no se aplican.


Conclusión

La combinación de Headscale y Headplane permite operar una VPN mesh moderna, controlada íntegramente en infraestructura propia y con una capa gráfica que simplifica la gestión diaria. La separación clara entre contenedores, configuraciones y políticas facilita el mantenimiento, las actualizaciones y la evolución futura del entorno sin introducir acoplamientos innecesarios.


Referencias