Problema
En muchos homelabs el entusiasmo por añadir hardware, VLANs y contenedores lleva a una arquitectura que funciona, pero que rápidamente se vuelve difícil de mantener. El patrón típico es:
- Un servidor Proxmox que aloja varios LXCs no privilegiados.
- Múltiples VLANs creadas en un switch gestionado para separar tráfico de gestión, laboratorio, invitados y dispositivos de confianza.
- Un firewall virtual (Debian o similar) que actúa como puerta de enlace entre esas VLANs y el ISP.
- Herramientas de orquestación caseras que intentan automatizar la creación de redes y contenedores.
El síntoma más común es que, tras añadir una nueva VLAN o LXC, aparecen problemas de conectividad inter‑VLAN, reglas de firewall que no se aplican o contenedores que pierden acceso a recursos críticos (DNS, NTP, almacenamiento). La raíz del problema suele estar en la falta de una guía estructurada que una la configuración de Proxmox, el switch gestionado y la orquestación de contenedores.
Causa
-
Diseño de VLAN sin documentación
Cuando se crean VLANs “sobre la marcha”, los IDs pueden solaparse con los de la red doméstica o con los rangos usados por los contenedores. Además, la asignación de puertos trunk vs access a menudo se hace de forma ad‑hoc, lo que genera loops o tráfico no etiquetado. -
Puentes de red (vmbr) mal alineados
Proxmox permite crear puentes que pueden ser “tagged” o “untagged”. Si un puente está configurado como no tagged pero se conecta a un puerto trunk, los paquetes llegan sin la etiqueta VLAN esperada y el firewall no los reconoce. -
Contenedores LXC no privilegiados sin permisos de red adecuados
Los LXCs sin privilegios dependen de la capa de red del host. Si el host no expone la VLAN correcta al contenedor, éste queda aislado o, peor, comparte la misma subred que otro contenedor, provocando colisiones de IP. -
Reglas de firewall dispersas
Tener una regla de NAT en la VM firewall y otra regla de filtrado en el propio Proxmox puede crear excepciones inesperadas. Cuando se añaden rutas estáticas (por ejemplo, para Tailnet o AirVPN), la tabla de rutas del host se vuelve inconsistente. -
Orquestador casero sin idempotencia
Scripts que crean puentes, asignan VLANs y despliegan LXCs sin comprobar el estado actual pueden volver a crear recursos, dejando interfaces “dangling” y duplicando configuraciones.
Solución
Adoptar un flujo de trabajo basado en tres capas claramente definidas:
-
Definir la topología de VLAN en un único archivo declarativo
Utiliza un formato sencillo (YAML o JSON) que describa cada VLAN: ID, nombre, subred, puertos del switch y puentes de Proxmox. Mantén este archivo bajo control de versiones. -
Configurar los puentes de Proxmox a partir de la definición
- Crea un puente “trunk” que reciba todas las VLANs del switch.
- Para cada VLAN, crea un puente “tagged” que apunte al trunk y añada la etiqueta correspondiente.
- Asocia los puentes “tagged” a las VMs o contenedores que necesiten acceso a esa VLAN.
-
Desplegar LXC con una plantilla que reciba la VLAN como parámetro
- Usa
pct createcon la opción-netXpara especificar el puente y la etiqueta. - Marca el contenedor como
unprivilegedy asigna unuidmap/gidmapque permita acceso a los dispositivos de red necesarios.
- Usa
-
Centralizar el firewall en una única VM
- Configura todas las reglas NAT, filtrado y rutas en esa VM.
- Desactiva el firewall de Proxmox para evitar solapamientos.
- Exporta la tabla de rutas del firewall a los hosts mediante un script de arranque que actualice
ip route.
-
Automatizar con Ansible (o tu orquestador) usando módulos idempotentes
- Un playbook que lea la definición de VLAN, aplique la configuración de puentes y despliegue los contenedores.
- Incluye tareas de verificación (
assert) para confirmar que cada puente tiene la etiqueta correcta y que cada LXC tiene la IP esperada.
Paso a paso resumido
-
Archivo de topología (vlan.yml)
vlans: - id: 10 name: LAB_TRANSIT subnet: 10.10.0.0/16 switch_ports: [1,2] # trunk ports - id: 20 name: LAB_INFRA subnet: 10.20.0.0/24 switch_ports: [3] # access -
Playbook Ansible (setup.yml)
- Lee
vlan.yml. - Crea
vmbr0(trunk) si no existe. - Por cada VLAN, crea
vmbr{id}conbridge_ports: vmbr0ybridge_vlan_aware: yes. - Usa
pct createpara lanzar contenedores con-net0 name=eth0,bridge=vmbr{id},tag={id}.
- Lee
-
Reglas de firewall en la VM
- Permitir tráfico intra‑VLAN.
- NAT para salida a internet desde VLANs de laboratorio.
- Rutas estáticas para redes externas (Tailnet, AirVPN).
Cuándo aplicar esta solución
- Escenarios con más de dos VLANs y la necesidad de aislar tráfico de gestión, laboratorio y dispositivos de invitados.
- Entornos donde se usan contenedores LXC no privilegiados y se requiere que cada uno pertenezca a una subred distinta.
- Cuando la configuración actual está dispersa entre scripts manuales, la UI de Proxmox y la consola del switch, y los cambios frecuentes generan inconsistencias.
No es necesario si tu homelab consta de un solo segmento de red y pocos contenedores; la sobre‑ingeniería puede ser más costosa que útil.
Código
# Crear puente trunk (vmbr0) si no existe
pvesh create /nodes/$(hostname)/network/interfaces -iface vmbr0 -type bridge -bridge_ports eth0 -autostart 1
# Crear puente VLAN 10 (vmbr10) sobre el trunk
pvesh create /nodes/$(hostname)/network/interfaces -iface vmbr10 -type bridge -bridge_ports vmbr0 -bridge_vlan_aware 1 -autostart 1
# Lanzar un LXC no privilegiado en VLAN 10
pct create 101 local:vztmpl/debian-12-standard_12.0-1_amd64.tar.gz \
-hostname infra01 -net0 name=eth0,bridge=vmbr10,tag=10,ip=10.10.1.10/16 \
-unprivileged 1 -features nesting=1 \
-memory 2048 -swap 512 -rootfs local-lvm:8
Verificación
-
Puentes
ip -d link show vmbr10 | grep vlanDebería mostrar
vlan protocol 802.1Q id 10. -
Conectividad LXC
pct exec 101 -- ping -c 3 10.10.1.1 # ping a la puerta del firewall pct exec 101 -- ip aLa interfaz
eth0debe tener la IP10.10.1.10/16y la etiqueta VLAN 10. -
Reglas de firewall
En la VM firewall:iptables -L -n -v | grep 10.10Verifica que exista la regla de NAT para la subred
10.10.0.0/16. -
Rutas
ip route show table main | grep 10.10Debe aparecer la ruta predeterminada hacia la VM firewall.
Notas adicionales
- Persistencia en el switch: guarda la configuración del puerto trunk y los puertos access antes de aplicar cambios desde Proxmox. Un error típico es que el switch siga etiquetando paquetes que el host espera sin etiqueta.
- UID/GID mapping: en contenedores no privilegiados, asigna rangos de UID/GID que no colisionen con los del host para evitar problemas con volúmenes compartidos.
- Backup de la topología: exporta
vlan.ymly el playbook a un repositorio Git; así cualquier reinstalación de Proxmox puede recrear la red automáticamente. - Monitoreo: usa una herramienta ligera (por ejemplo, Gatus o Prometheus Node Exporter) para alertar cuando una VLAN pierde conectividad o cuando un LXC no responde al ping de salud.
- Escalabilidad: al añadir nuevas VLANs, solo necesitas actualizar
vlan.ymly volver a ejecutar el playbook; no hay cambios manuales en Proxmox ni en el switch.