SSD Nodes Learn 🎉 VPS desde $5.50/mes
Guías Matt ConnorPor Matt Connor · Actualizado 2026-08-21

Cómo configurar contenedores Incus en un VPS

Aprende a configurar Incus en un VPS con comprobaciones de virtualización, pools de almacenamiento y red, y detecta qué puede fallar al iniciar.

Qué es un contenedor de sistema de Incus

Los contenedores de sistema de Incus en un VPS proporcionan una máquina completa con su propio sistema de init y sus propias cuentas de usuario. No son un único proceso con un sistema de archivos asociado. El contenedor arranca, ejecuta un proceso init como PID 1 y responde a systemctl. Comparte el kernel del host, por lo que no es una máquina virtual. Todo lo que está por encima del kernel se comporta como un sistema independiente.

Incus es el fork comunitario de LXD y se mantiene dentro del proyecto Linux Containers. El comando cliente es incus. También ejecuta máquinas virtuales reales mediante QEMU cuando se indica --vm, pero el contenedor de sistema es el motivo por el que la mayoría de los usuarios instala Incus. Es el tipo de contenedor que se trata en el resto de esta guía.

Por qué las comparaciones con Docker inducen a error

Docker empaqueta un proceso. Incus empaqueta un sistema operativo. La documentación de Incus expone claramente esta diferencia: "Los contenedores de aplicaciones (como los que proporciona Docker) empaquetan un único proceso o aplicación. En cambio, los contenedores de sistema simulan un sistema operativo completo, similar al que se ejecutaría en un host o en una máquina virtual."

Esta diferencia cambia la forma de trabajar con el contenedor a diario.

  • Una imagen de Docker no tiene init, por lo que systemctl falla en su interior. Un contenedor de Incus ejecuta un sistema init, por lo que los servicios y los temporizadores funcionan como en un servidor.
  • Un contenedor de Docker está pensado para destruirse y reconstruirse a partir de un Dockerfile. Un contenedor de Incus está pensado para conservarse, actualizarse y protegerse mediante snapshots.
  • Una imagen de Docker es un artefacto de compilación que se sube a un registro. Una instancia de Incus es estado almacenado en disco dentro de un pool de almacenamiento, y se mueve con incus export.
  • Docker aísla una carga de trabajo. Incus aísla una máquina, por lo que un contenedor puede alojar varias cargas de trabajo y varias cuentas de usuario.

Puede ejecutar Docker dentro de un contenedor de sistema de Incus. No ejecutaría Incus dentro de un contenedor de aplicaciones de Docker. Si lo que realmente necesita es un proceso por contenedor con un paso de compilación de imagen, Podman y Docker en un VPS es la comparación que debe leer primero. Si quiere un kernel independiente por carga de trabajo en lugar de uno compartido, Firecracker microVMs en un VPS ofrece el enfoque contrario.

¿Incus se ejecutará dentro de un VPS?

Depende del tipo de virtualización de su VPS y de su kernel. Compruebe ambos datos antes de instalar nada. No se base únicamente en la página comercial del proveedor. Ejecute estos cuatro comandos en el equipo.

systemd-detect-virt
uname -r
stat -fc %T /sys/fs/cgroup
cat /sys/fs/cgroup/cgroup.controllers

systemd-detect-virt al mostrar kvm o qemu significa que su VPS es una máquina virtual con su propio kernel. Este es el caso sencillo, porque Incus se comporta igual que en hardware físico. Mostrar lxc, lxc-libvirt o openvz significa que su VPS es un contenedor que comparte el kernel del proveedor. Los contenedores de Incus que se ejecutan dentro son contenedores anidados, y el anidamiento sólo funciona si el proveedor lo habilitó en su contenedor. No puede habilitarlo desde dentro, porque el ajuste se encuentra en el host, que usted no controla.

stat -fc %T /sys/fs/cgroup debería mostrar cgroup2fs. Cualquier otro resultado significa que el equipo usa una disposición cgroup (grupo de control) v1 o híbrida, que las versiones actuales de Incus no tienen como objetivo.

cat /sys/fs/cgroup/cgroup.controllers muestra los controladores de grupos de control que se le han delegado. La documentación de Incus indica que blkio, cpuset, devices, freezer, memory y pids son necesarios. En un VPS anidado, esa lista suele ser más corta que en uno basado en KVM, porque el proveedor decide qué controladores delega. Si falta un controlador en ese archivo, Incus no puede usarlo. Por tanto, el límite de instancias que depende de él no estará disponible.

La versión del kernel es más importante que antes. En agosto de 2026, la documentación de Incus indica dos requisitos mínimos diferentes para las dos ramas que mantiene el proyecto upstream. La rama 6.0 LTS (soporte a largo plazo) indica: "La versión mínima compatible del kernel es 5.4." La rama estable actual indica: "La versión mínima compatible del kernel es 6.12." Ubuntu 24.04 proporciona la serie 6.0 LTS en su propio repositorio y la combina con un kernel 6.8, una combinación compatible. Si instala la compilación estable actual desde el repositorio upstream en ese mismo kernel 6.8, estará por debajo del mínimo documentado. Por tanto, lea uname -r antes de elegir un repositorio.

Si su objetivo son máquinas virtuales completas en lugar de contenedores, la limitación es diferente y más difícil de resolver. Consulte virtualización anidada en un VPS para saber si su VPS puede exponer /dev/kvm, y Proxmox frente a un VPS alquilado si el hardware es suyo.

Instalar Incus en Ubuntu o Debian

Debian 13 y Ubuntu 24.04 y versiones posteriores incluyen Incus en sus propios repositorios.

sudo apt update
sudo apt install -y incus

En Debian, incus-base instala la compatibilidad con contenedores sin los componentes de máquinas virtuales. En Ubuntu, añada qemu-system si también quiere instancias de --vm.

Si necesita una versión más reciente que la disponible en su distribución, los paquetes del proyecto están en pkgs.zabbly.com. Estos comandos proceden del archivo README del repositorio oficial del proyecto.

sudo apt update && sudo apt install -y curl
sudo mkdir -p /etc/apt/keyrings/
sudo curl -fsSL https://pkgs.zabbly.com/key.asc -o /etc/apt/keyrings/zabbly.asc
sudo sh -c 'cat <<EOF > /etc/apt/sources.list.d/zabbly-incus-stable.sources
Enabled: yes
Types: deb
URIs: https://pkgs.zabbly.com/incus/stable
Suites: $(. /etc/os-release && echo ${VERSION_CODENAME})
Components: main
Architectures: $(dpkg --print-architecture)
Signed-By: /etc/apt/keyrings/zabbly.asc
EOF'
sudo apt-get update
sudo apt-get install -y incus

A continuación, permita que su usuario acceda al socket del daemon.

sudo usermod -aG incus-admin "$USER"
newgrp incus-admin
incus info

incus info muestra la configuración del servidor y confirma que el socket funciona. Un error de permisos indica que el cambio de grupo todavía no se ha aplicado al shell; newgrp incus-admin lo aplica al shell actual y un nuevo inicio de sesión lo aplica correctamente. Considere que pertenecer a incus-admin equivale a tener acceso root en el host, porque el acceso a ese socket proporciona control total sobre un daemon que se ejecuta como root. Algunas distribuciones también crean un grupo incus normal para el acceso restringido de usuarios.

Ahora inicialice el daemon.

sudo incus admin init

Responda a las preguntas en lugar de recurrir a incus admin init --minimal. La configuración mínima selecciona el controlador de almacenamiento dir, y la siguiente sección explica por qué esta elección afecta a la configuración posterior.

Inicie algo y confirme que funciona.

incus launch images:debian/13 web
incus list
incus exec web -- bash

incus list debería mostrar web como RUNNING, con una dirección IPv4 en la subred incusbr0. Si no aparece ninguna dirección, DHCP (protocolo de configuración dinámica de host) no se completó; la sección de red explica este problema. Un contenedor que no se puede iniciar muestra la causa en incus info web --show-log, y los errores del daemon aparecen en sudo journalctl -u incus -n 50. En un VPS donde systemd-detect-virt devolvió lxc o openvz, este inicio es la prueba real de si el anidamiento está disponible.

Por qué importa el backend de almacenamiento predeterminado

El backend de almacenamiento determina si una instantánea se crea al instante o si se hace una copia completa del disco del contenedor. Es la única decisión de la instalación que después no se puede cambiar de forma económica.

Incus admite dir, btrfs, lvm, zfs, Ceph y varios controladores remotos. En un VPS con un solo disco, la elección real está entre dir y btrfs.

El controlador dir mantiene cada contenedor como archivos y directorios normales en /var/lib/incus. Incus lo documenta como «mucho más lento que los demás controladores», porque tiene que descomprimir cada imagen y crear copias reales en lugar de referenciar bloques compartidos. Una instantánea de un contenedor de 4 GiB escribe 4 GiB y tarda tanto como cp -a. Las cuotas de disco sólo funcionan en ext4 o XFS con las cuotas de proyecto habilitadas en el nivel del sistema de archivos. Esta opción no está habilitada de forma predeterminada en la mayoría de las imágenes de VPS, por lo que un límite de disco en un pool dir suele no tener efecto.

btrfs y zfs usan copy-on-write, por lo que una instantánea sólo registra los bloques que cambian después de crearla. Incus recomienda estos dos backends. Las instantáneas se crean casi al instante. Las cuotas de disco funcionan mediante el soporte de cuotas propio del sistema de archivos.

La mayoría de los planes VPS proporcionan un solo disco sin una partición adicional, por lo que debe colocar el pool en un archivo de bucle. Incus lo hace automáticamente si no proporciona ningún source=.

sudo apt install -y btrfs-progs
incus storage create fast btrfs size=30GiB
incus profile device set default root pool=fast
incus launch images:debian/13 web2 -s fast

Sin size=, un pool respaldado por un dispositivo de bucle ocupa el 20% del espacio libre del disco, con un mínimo de 5 GiB y un máximo de 30 GiB. Establezca este valor de forma explícita. El archivo de bucle está en el sistema de archivos raíz, por lo que el pool y el host comparten el mismo espacio libre. Si el pool se llena, también se llena el disco del host.

ZFS en Debian y Ubuntu es un módulo DKMS, no un módulo integrado en el kernel. Por eso se recompila con cada actualización del kernel y puede fallar en alguna de ellas. En un servidor que no supervise a diario, btrfs requiere menos mantenimiento que las dos opciones.

Los tres modos de red y qué expone cada uno

incus admin init crea un bridge administrado llamado incusbr0 y conecta a él cada instancia nueva. Es una de las tres formas de conectar un contenedor. Las otras dos existen porque la primera oculta los contenedores detrás de NAT (traducción de direcciones de red).

Bridge administrado. incusbr0 obtiene una subred privada. El host conserva la primera dirección de esa subred y actúa como gateway. Incus ejecuta DHCP y DNS (sistema de nombres de dominio) en ella. El tráfico saliente usa la dirección pública del host, con NAT de origen. Nada externo puede llegar al contenedor hasta que se configure explícitamente. Reenvíe un puerto con un dispositivo proxy.

incus config device add web http proxy listen=tcp:0.0.0.0:8080 connect=tcp:127.0.0.1:80 nat=true

nat=true reenvía mediante reglas de netfilter en lugar de usar una conexión independiente en espacio de usuario. Por eso, la dirección real del cliente se conserva en los registros del contenedor. Incus admite este modo sólo cuando el host es el gateway de la instancia. Ese es exactamente el caso de incusbr0.

macvlan. El contenedor obtiene su propia dirección MAC (control de acceso al medio) en la red física del host. En la mayoría de las plataformas VPS esto falla porque el puerto del switch virtual está asociado a la dirección MAC de la VM y descarta las tramas de cualquier otra dirección. Incluso cuando funciona, existe otra limitación importante. Incus documenta que "los dispositivos macvlan, aunque pueden comunicarse entre sí y con el exterior, no pueden comunicarse con su dispositivo principal. Esto significa que no se puede usar macvlan si en algún momento las instancias necesitan comunicarse con el propio host".

Enrutado. Este es el modo que suele funcionar en un VPS con direcciones adicionales. Incus documenta el dispositivo como uno que "crea un par de dispositivos virtuales para conectar el host con la instancia y configura rutas estáticas y entradas de proxy ARP/NDP para permitir que la instancia se una a la red de una interfaz principal designada". ARP es el protocolo de resolución de direcciones. El contenedor conserva una dirección pública. El host responde a las solicitudes ARP para esa dirección, por lo que el proveedor sólo ve la dirección MAC del host.

incus config device add web eth0 nic nictype=routed parent=enp1s0 ipv4.address=203.0.113.20

Obtenga el nombre de la interfaz principal de ip route show default. Las imágenes actuales usan nombres como enp1s0 o ens3, y rara vez eth0. Al nombrar el dispositivo eth0 se reemplaza el dispositivo proporcionado por el perfil default. Por tanto, el contenedor termina conectado a la interfaz enrutada en lugar de al bridge. Compruebe el resultado desde dentro con ip a y ip route.

Por qué un contenedor pudo acceder a un servicio del host

Un contenedor en incusbr0 tiene su propio espacio de nombres de red. No tiene una frontera de firewall frente al host. El host está en ese bridge con la dirección de gateway, por lo que, desde el contenedor, el host es un vecino directamente accesible y todos los servicios del host que escuchen en 0.0.0.0 responden allí.

Compruébelo. En el host, liste los servicios que están escuchando.

sudo ss -tlnp

Después, desde un contenedor, apunte al gateway que muestra ip route.

ip route show default
nc -zv 10.0.0.1 6379

Si una base de datos, un endpoint de métricas o un panel de administración del host escucha en 0.0.0.0, la comprobación tiene éxito. El firewall de red de su proveedor nunca vio el paquete porque el paquete nunca salió de la máquina. Esta es la causa de la mayoría de las preguntas del tipo «¿cómo pudo acceder a eso?»: NAT aísla el contenedor de Internet, pero nada lo aísla del host.

Vincule los servicios del host a 127.0.0.1 siempre que sea posible. Después, filtre el bridge en el host. En un equipo con ufw, la política predeterminada de denegación ya bloquea el tráfico del contenedor al host. Esto interrumpe el DNS y DHCP de Incus, y la solución indicada en la documentación de Incus es sudo ufw allow in on incusbr0. Ese único comando vuelve a abrir todos los puertos del host para todos los contenedores. En su lugar, permita sólo lo que los contenedores necesiten realmente.

sudo ufw allow in on incusbr0 to any port 53 proto udp
sudo ufw allow in on incusbr0 to any port 53 proto tcp
sudo ufw allow in on incusbr0 to any port 67 proto udp
sudo ufw route allow in on incusbr0
sudo ufw route allow out on incusbr0

Las dos reglas ufw route son las que permiten que el tráfico de las instancias atraviese el host hacia Internet. Sin ellas, la política de enrutamiento de ufw descarta los paquetes reenviados, por lo que los contenedores obtienen una dirección, pero no pueden acceder a nada.

Instantáneas y perfiles

Una instantánea es una copia de la instancia en un momento concreto dentro de su pool de almacenamiento.

incus snapshot create web pre-upgrade
incus info web
incus snapshot restore web pre-upgrade
incus snapshot delete web pre-upgrade

incus info web muestra las instantáneas que tiene la instancia. Prográmelas por instancia.

incus config set web snapshots.schedule=@daily
incus config set web snapshots.expiry=4w

Una instantánea reside en el mismo pool, en el mismo disco y en el mismo servidor. Protege frente a una actualización defectuosa. No protege frente a un disco averiado ni frente a la eliminación de una instancia. La copia de seguridad es incus export y el archivo debe salir del servidor.

incus export web /root/web-backup.tar.gz
incus import /root/web-backup.tar.gz

Un perfil es un conjunto con nombre de claves de configuración y dispositivos que se aplica a las instancias. Todas las instancias reciben el perfil default salvo que se indique lo contrario, y ese perfil proporciona su disco raíz y su interfaz de red. Editar default cambia todas las instancias que lo utilizan. Esto resulta útil, pero también permite desconectar la red de veinte contenedores de una sola vez.

incus profile create small
incus profile set small limits.memory=512MiB
incus profile set small limits.cpu=1
incus launch images:debian/13 api -p default -p small

Los perfiles se aplican en orden, por lo que prevalece la clave definida en el último perfil de la lista. Consulte la configuración final efectiva de una instancia con incus config show api --expanded.

Ejecutar Docker dentro de un contenedor Incus

Docker dentro de un contenedor de sistema Incus necesita que el anidamiento esté habilitado, porque Docker crea sus propios espacios de nombres y montajes, y un contenedor no puede crearlos de forma predeterminada.

incus config set web security.nesting=true
incus restart web

Incus documenta security.nesting como «Si se permite el anidamiento dentro de la instancia», y su valor predeterminado es false para los contenedores. Otros dos puntos aparecen directamente en las preguntas frecuentes de Incus. Un contenedor no puede cargar módulos del kernel, por lo que cualquier módulo que necesite Docker debe cargarse en el host y aparecer en incus config set web linux.kernel_modules overlay,br_netfilter. Además, crear un archivo /.dockerenv dentro del contenedor hace que Docker omita algunas comprobaciones que fallan en un entorno anidado.

En hosts Ubuntu 24.04, las restricciones de AppArmor para los espacios de nombres de usuario sin privilegios pueden bloquear el pivot_root que realiza runc. Docker dentro del contenedor muestra:

failed to create shim task: OCI runtime create failed: runc create failed: unable to start container process: error during container init: error jailing process inside rootfs: pivot_root .: permission denied

y dmesg del host muestra una línea que contiene apparmor="DENIED" operation="pivotroot" class="mount". El ajuste que se suele probar es kernel.apparmor_restrict_unprivileged_userns. Desactivarlo no es una solución fiable: el informe de error de Incus para esta denegación concreta indica que establecerlo en 0 no la resolvió. Lea primero dmesg para revisar la denegación y confirmar si AppArmor es realmente el problema antes de cambiar un valor de seguridad predeterminado.

Si prefiere ejecutar los contenedores directamente en el VPS y eliminar una capa, ejecutar Docker en un VPS explica esa configuración por separado.

Modos de fallo y mensajes que verá

Las instancias pierden toda la conectividad de red después de instalar Docker en el host. La documentación de Incus indica la causa: "Docker establece la política global de FORWARD en drop, lo que impide que Incus reenvíe tráfico y provoca que las instancias pierdan la conectividad de red." Las instancias conservan sus direcciones, pero no pueden comunicarse. Establezca ip-forward-no-drop en true en /etc/docker/daemon.json. Después, haga persistente el reenvío y permita el tráfico del bridge mediante la propia cadena de Docker.

echo "net.ipv4.conf.all.forwarding=1" | sudo tee /etc/sysctl.d/99-forwarding.conf
sudo systemctl restart systemd-sysctl
sudo iptables -I DOCKER-USER -i incusbr0 -j ACCEPT
sudo iptables -I DOCKER-USER -o incusbr0 -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT

Esas reglas de iptables no sobreviven por sí solas a un reinicio. Hágalas persistentes.

Los contenedores dejan de iniciarse y muestran un error de cgroup. La FAQ de Incus documenta este caso. Un mensaje sobre Failed to mount "/sys/fs/cgroup" suele indicar que un cliente VPN del host montó el controlador de cgroup v1 net_cls sobre cgroup v2, que es el que usa Incus. sudo umount /sys/fs/cgroup/net_cls lo corrige.

La instancia no obtiene una dirección IPv4. incus list muestra que está en ejecución, pero la columna de direcciones está vacía. El host está descartando las respuestas DHCP. Lo más habitual es que el firewall del host no conozca el bridge. En ufw, sudo ufw allow in on incusbr0 to any port 67 proto udp lo corrige. Supervise la llegada de las solicitudes con sudo tcpdump -ni incusbr0 port 67.

La instancia no se inicia en un VPS anidado. Revise primero incus info <name> --show-log y después sudo journalctl -u incus -n 50. Si systemd-detect-virt mostraba lxc o openvz, el problema está en el proveedor. Ningún ajuste dentro de su VPS puede corregirlo.

Las snapshots son lentas y el disco sigue llenándose. Está usando un pool dir. incus storage list muestra el driver de cada pool. Para cambiar a un pool con copy-on-write, cree el pool nuevo y copie las instancias con incus copy web web-new -s fast. Después, elimine las originales cuando haya comprobado que las copias se inician correctamente.

FAQ

¿Un contenedor de Incus es lo mismo que un contenedor de Docker?

No. Docker empaqueta un único proceso o una aplicación. Un contenedor de sistema de Incus simula un sistema operativo completo, con su propio init, sus propios usuarios, sus propios servicios y su propio gestor de paquetes. Un contenedor de Incus se conserva y se actualiza como un servidor. Un contenedor de Docker se elimina y se vuelve a crear a partir de una imagen. Puede ejecutar Docker dentro de un contenedor de Incus estableciendo security.nesting=true en el contenedor. Lo contrario no funciona.

¿Puedo ejecutar Incus en un VPS?

En un VPS KVM, sí. Si systemd-detect-virt muestra kvm o qemu, tiene su propio kernel e Incus se comporta igual que en hardware físico. Si muestra lxc, lxc-libvirt o openvz, su VPS es a su vez un contenedor, por lo que los contenedores de Incus están anidados y sólo funcionan si el proveedor habilitó el anidamiento en su contenedor. Compruebe también uname -r, porque en agosto de 2026 la rama estable actual de Incus documenta un kernel mínimo de 6.12, mientras que la rama 6.0 LTS documenta 5.4.

¿Qué backend de almacenamiento debo elegir para Incus en un VPS?

btrfs en un archivo de loop, a menos que tenga un dispositivo de bloques disponible para asignárselo. El controlador dir está documentado como mucho más lento que los demás, porque copia archivos en lugar de usar copy-on-write, por lo que cada snapshot vuelve a escribir todo el contenedor. incus admin init --minimal selecciona dir, por lo que merece la pena responder las preguntas interactivas durante esos dos minutos. Cree el pool con incus storage create fast btrfs size=30GiB.

¿Por qué mi contenedor de Incus puede acceder a un servicio que se ejecuta en el host?

Porque el bridge incusbr0 predeterminado coloca el host en la misma subred que el contenedor, en la dirección de gateway, y no hay ningún filtro entre ellos. Cualquier servicio del host enlazado a 0.0.0.0 responde en esa dirección, y el firewall del proveedor nunca ve esos paquetes porque no salen de la máquina. Enlace los servicios del host a 127.0.0.1 y, en un host con ufw, permita únicamente DNS y DHCP en incusbr0 en lugar de usar la regla general sudo ufw allow in on incusbr0.

¿Cómo hago una copia de seguridad de un contenedor de Incus?

incus export web /root/web-backup.tar.gz escribe la instancia y sus snapshots en un único archivo, y incus import la restaura en el mismo servidor o en otro. Los snapshots creados con incus snapshot create no son copias de seguridad: permanecen en el mismo pool de almacenamiento y en el mismo disco, por lo que sobreviven a una actualización defectuosa, pero no a un fallo del servidor. Prográmelos con incus config set web snapshots.schedule=@daily y copie las exportaciones fuera del equipo.

#incus#lxd#system-containers#virtualization#vps