Introducción
Un contenedor es una opción de virtualización que permite ejecutar un conjunto de procesos de forma que se encuentren completamente aislados del resto de procesos que puedan estar ejecutándose en un sistema.
Esto implica que, aunque los procesos del contenedor estén utilizando el sistema operativo del anfitrión, están utilizando un root file system virtual propio del contenedor; con sus propias versiones de librerías, datos y dispositivos, independientes a los existentes en el sistema anfitrión u otros contenedores del sistema.
Para quienes tengan experiencia en sistemas tipo Unix, esta solución sería equivalente a ejecutar procesos «enjaulados» con chroot. Salvo que, en las soluciones de contenedores, se simplifican todas las tareas de administración, como la gestión de los root file systems virtuales así como los límites de recursos y permisos de usuarios.
Ventajas e inconvenientes
La principal ventaja del uso de contenedores por sobre otras alternativas de virtualización consiste en que, como se está compartiendo el uso del sistema operativo anfitrión, se evita el overhead asociado a la emulación y compartición de dispositivos.
Por contrapartida, al estar compartiendo el sistema operativo del sistema anfitrión, el código de los contenedores debe mantener compatibilidad binaria con el sistema operativo en servicio. En general, dada la compatibilidad del kernel de Linux, no existen problemas para ejecutar contenedores de distribuciones completamente dispares al sistema anfitrión siempre que sean de la misma arquitectura. Por ejemplo, se puede perfectamente ejecutar un contenedor Debian para x86 de 32bits desde un anfitrión en CentOS ejecutando un kernel para x86 de 64 bits. Pero no se podrá ejecutar un contenedor armhf salvo que nuestro anfitrión sea también armhf.
Eventualmente, podrían aparecer efectos secundarios indeseados en el uso de contenedores, por ejemplo en el uso de dispositivos tipo loopback o en la gestión de dispositivos dinámicos como unidades USB que se conecten o desconecten luego de iniciado el contenedor. Pero, en general, no existen limitaciones acerca de las posibilidades de ejecución de un contendor, salvo por los límites especificados a la hora que el contenedor se inicia en cuanto a cuota de disco asignada o restricciones en la RAM o número de cores disponibles.
LXC
La solución básica para contenedores en ambiente Linux es LXC, que utiliza facilidades incluidas en el kernel a partir de la versión 2.6.29.
La administración se basa en un conjunto de comandos bajo la forma lxc-comando
y si bien es completamente operativa como tal, suele ser la base para otras tecnologías.
La principal diferencia con respecto a otro tipo de soluciones como podría ser Docker (que originalmente también estuvo basado en lxc pero que en la actualidad utiliza su propia tecnología de virtualización) es que, mientras que en Docker los contenedores generan entornos de ejecución de aplicaciones con independencia del Sistema Operativo donde se encuentren soportados, lxc provee contenedores que contienen una imagen completa de un Sistema. O sea que en un contenedor lxc tendremos acceso a un prompt de sistema, scheduler de procesos, configuración de red y, en general, todos los recursos como si tratase de una máquina virtual pudiendo cargar las herramientas y paquetes que deseemos (salvo, claro está, por la imagen del kernel del sistema operativo en sí que siempre será el del anfitrión).
LXD
lxd es una de las soluciones que, si bien están utilizando lxc para su operación, posee una serie de características que simplifican la administración de contenedores y otorgan una serie de ventajas adicionales como ser:
-
- API RESTful de administración y administración remota
- Gestión avanzada de recursos (CPU, memoria, disco, red, uso del kernel)
- Gestión avanzada de trasvase de dispositivos (device passthrough)
- Integración con OpenStack
- Integración con soluciones de almacenamiento avanzada. Soporte de múltiples backends incluyendo pools de almacenamiento y volúmenes dinámicos
Estando basado en lxc, lxd mantiene un alto grado de compatibilidad con este sistema. Y así como lxc tenía comandos bajo la sintaxis lxc-comando
, lxd tendrá comandos bajo la forma lxc comando
, manteniendo el nombre del comando en la mayoría de los casos.
ZFS
El file system Z es un sistema de ficheros desarrollado originalmente por Sun Microsystems para sus sistemas Solaris y que cuenta con una serie de características que lo hace ideal para soluciones de almacenamiento como ser:
-
- Escalabilidad. Posibilidad de gestionar hasta zettabytes de información, distribuibles en pools de dispositivos.
- Integridad. Todos los bloques de datos llevan un checksum asociado que aseguran la consistencia del contenido.
- Raid software. Soportando configuraciones RAID0, RAID1, RAIDZ (versión mejorada de RAID5 y RAID6) sin necesidad de ningún hardware particular.
- Funcionalidad Copy on write. Ahorro de espacio y coste 0 en funciones de copia.
En particular se incluye la referencia a este sistema por su alto grado de integración con LXD. Desde el comienzo de la configuración del servicio con el comando lxd init
se nos ofrece la posibilidad de definir un contenedor ZFS y, mi recomendación es utilizar esta opción dada las ventajas que ofrece la funcionalidad copy on write para la gestión de snapshots, clonación de imágenes gestión del espacio disponible.