Herramientas de usuario

Herramientas del sitio


informatica:sistemas_operativos:cursos:docker_a_fondo_introduccion_kubernetes:introduccion_docker

¡Esta es una revisión vieja del documento!


Introducción a Docker

Prerrequisitos e instalación

Para seguir correctamente el curso, el único prerrequisito es disponer de un ordenador con cualquier sistema operativo reciente actualizado y Docker Engine (en Linux) o Docker Desktop instalado (en Linux, Windows o MacOS).

Docker Engine es un producto gratuito y open source. Por su parte Docker Desktop es más bien una suma de varios productos, algunos de los cuales son closed source y su uso está restringido por licencia, no siendo gratuito en todos los casos. Pero ¡no te asustes!: si vas a hacer un uso personal de Docker Desktop es completamente gratuito. Si el uso que harás es empresarial, tendrías que pagar tan solo si tu empresa tiene más de 200 trabajadores o factura más de 10 millones de dólares, pudiendo usar la edición gratuita si no es así.

Docker Engine existe para Linux mientras que Docker Desktop existe para Linux, MacOS y Windows, por lo que el sistema operativo que uses no es problema (aunque más adelante habrá ciertos apartados propios de Windows únicamente).

Adicionalmente se asume cierta experiencia en la interfaz de línea de comandos (terminales bash en Linux/macOS; símbolo del sistema y Powershell en Windows).

¿Linux, Windows o Mac?

El curso se puede seguir en cualquier sistema operativo, ya sea Windows, Linux o Mac. En el caso de entornos Windows la única condición es que Docker for Desktop se pueda instalar en la versión concreta de Windows.

La gran mayoría del curso aplica igual y sin diferencias a los tres sistemas operativos, pero hay algunos aspectos avanzados que pueden referirse a sólo uno de ellos:

  • Cuando hablemos de contenedores Windows, el contenido afecta solamente a Windows, ya que es el único SO que puede ejecutarlos.
  • Cuando hablemos de aspectos avanzados (en concreto temas de seguridad y permisos), los contenidos harán referencia básicamente a Linux, ya que es el SO donde se pueden experimentar y ver con más facilidad (al no haber una capa intermedia que ejecute los contenedores). En Windows y Mac, algunos temas referentes a seguridad experimentan ligeras variaciones que dependen exactamente de la configuración del sistema.
  • Cuando hablemos de cómo funcionan los contenedores, nos referimos básicamente a contenedores Linux. Aunque en el apartado de “Contenedores Windows” se menciona un poco el funcionamiento de contenedores Windows, en el resto del curso se asume que estás usando contenedores Linux (aunque tu máquina sea Windows o Mac)

Instalación de Docker Engine o Desktop

Para instalar Docker Engine, dirígete a la documentación de Docker y sigue las instrucciones correspondientes a tu distro de Linux.

Para instalar Docker Desktop, dirígete a la página de Docker Desktop y sigue las instrucciones de tu sistema operativo.

Recuerda que en Windows y MacOS debes instalar Docker Desktop. En Linux puedes elegir entre Docker Engine (la versión gratuita y Open Source) o Docker Desktop.

Si estás en Windows, espera a la próxima lección antes de instalarlo, puesto que puede influir la versión que tengas o si tienes habilitadas o no ciertas características.

Docker Engine versus Docker Desktop

Como se ha comentado antes, Docker Desktop es más bien un conjunto unificado de varios productos destinados a permitir el uso de Docker Engine en aquellos sistemas donde no se encuentra disponible. Eso te puede sonar confuso, así que voy a intentar explicártelo :-)

Docker Engine existe solo para Linux (y Windows Server, aunque podemos obviarlo por el momento: trataremos ese caso en el módulo opcional de contenedores Windows). Así, si trabajas en Linux, te basta con instalar directamente Docker Engine y obtienes los siguientes componentes:

  • El cliente (el comando docker), que usa la línea de comandos (CLI).
  • El componente servidor, que crea y ejecuta los contenedores.

El cliente de línea de comandos (docker) sí que existe para Windows y MacOS, pero obviamente requiere del componente servidor y ese solo existe en Linux. Dado que los contenedores los ejecuta el servidor y un contenedor no virtualiza, eso implica una cosa: solo puedes usar contenedores que sean binarios Linux.

Ojo, que esta última afirmación no es del todo cierta (es posible ejecutar contenedores binarios Windows, pero eso lo veremos más adelante, ya que es un escenario distinto).

Entonces la situación que tenemos es que, realmente se requiere de Linux para ejecutar contenedores. Pero la gente de Docker era (y es) consciente de que muchos desarrolladores usan Windows o MacOS y de ahí que sacaran Docker Desktop para esos dos sistemas. Docker Desktop permite ejecutar la parte servidora de Docker en Windows o MacOS. Dado que esta parte servidora existe solo en Linux, Docker Desktop recurre a la virtualización para conseguirlo.

Así, cuando instalas Docker Desktop, se instala también una máquina virtual (MV) Linux en tu sistema y esa MV es la que ejecutará la parte servidora de Linux, y por lo tanto los contenedores. Al instalar Docker Desktop también obtenemos el cliente nativo (el comando docker, para Windows o MacOS), configurado de tal modo que automáticamente se conecta a dicha MV sin que nosotros tengamos que hacer nada: tú usas el comando docker desde una línea de comandos Windows o un terminal de MacOS y automáticamente se comunica con la parte servidora ejecutándose en la VM. Esa MV la configura y aprovisiona Docker Desktop automáticamente y no tienes que hacer nada con ella (ni pararla, ni configurarla, ni encenderla, ni nada de nada).

  • En Windows puedes usar Hyper-V o WSL2 siendo ese último el modo recomendado por rendimiento
  • En MacOS usa xhyve
  • En Linux usa KVM (sí, Docker Desktop en Linux también usa una máquina virtual)

Además, Docker Desktop añade los siguientes componentes:

  • Una pequeña interfaz gráfica de configuración en el caso de Docker Desktop (inexistente en Docker Engine)
  • La integración de herramientas adicionales como Synk o Compose
  • La posibilidad de ejecutar un Kubernetes de desarrollo

Pero lo que debes tener claro es que cuando hablamos de crear y administrar contenedores no hay diferencia alguna entre Docker Desktop y Docker Engine.

Resumiendo: Docker Desktop es un producto que integra Docker Engine junto con una VM para permitir de forma fácil el uso de contenedores Linux en Windows y MacOS. Además, tiene pequeños añadidos como una pequeña interfaz gráfica y la posibilidad de ejecutar un Kubernetes de desarrollo.

Inicialmente Docker Desktop existía solo para Windows y MacOS, pero posteriormente salió también para Linux, ofreciendo las mismas características adicionales que ofrecía en Windows y Mac (como p.ej. el soporte para Kubernetes integrado).

El coste de Docker Desktop

A diferencia de Docker Engine, Docker Desktop no es un producto gratuito en todos los casos. Recuerda que no existe Docker Engine para Windows o MacOS, así que, dependiendo de la situación de tu empresa, es posible que esta deba licenciar el producto. Digo “empresa” porque Docker ha declarado que tiene la intención de que el producto siga siendo gratuito para “uso personal o de enseñanza” y, efectivamente, así es. En la página de precios puedes consultar las distintas opciones y en qué casos es obligatorio alguno de los planes de pago. Esos planes incorporan algunas características adicionales, así que también se puede dar el caso de que a tu empresa le interese contratar alguno de ellos a pesar de no estar legalmente obligada. En la página de precios están detallados todos los planes, sus características y en qué casos es legalmente obligatorio contratar alguno de ellos.

Verificación de la instalación de Docker

Para verificar qué Docker está instalado en tu máquina, abre una CLI y teclea:

docker --version

Deberías ver la versión de Docker instalada. Cualquier versión mínimamente moderna te servirá para seguir el curso. Te recomiendo que uses la última que esté disponible para poder aprovechar todas sus características.

El comando docker --version muestra por consola la versión del motor de Docker. En el caso de Docker Engine (Linux), esa es la versión del producto. En el caso de Docker Desktop, puedes verla accediendo a la opción About Docker Desktop del menú contextual:

Siempre que en esta formación hablemos de “versión de Docker” nos referiremos a la versión del motor (engine).

Instalación de Docker en Windows

Recuerda que los contenedores NO son un mecanismo de virtualización y que, al final, la aplicación que contiene el contenedor es ejecutada por el SO real, el del host. Dicho SO debe tener, por lo tanto, soporte para ejecutar contenedores. En Linux ya hace algunos años que existe dicho soporte, pero en Windows no siempre ha sido así.

El soporte para contenedores en Windows llegó con Windows Server 2016 y Windows 10 Anniversary Edition. Eso significa que un contenedor Windows (un contenedor que tenga binarios de Windows) solo puede ser ejecutado si tienes una versión del sistema operativo igual o posterior a las indicadas. Eso implica que en Linux el escenario de los contenedores está bastante avanzado y en Windows lleva menos tiempo en funcionamiento.

Pero Docker Desktop for Windows se puede instalar, incluso, en versiones anteriores de Windows a las mencionadas. Entonces, ¿qué es lo que ocurre exactamente? Pues bien, depende de la versión de Docker Desktop y de Windows que tengamos.

En general, si tienes una versión reciente y actualizada de Windows (que sería lo recomendable), deberías instalar Docker Desktop integrado con el subsistema Linux de Windows (WSL 2), como veremos ahora mismo.

En esta lección verás, antes de nada, cómo instalar Docker Desktop en versiones recientes de Windows, que será lo que harás habitualmente. Pero, como es posible que debas instalarlo en versiones sin ese soporte, también tienes un apartado que te explica cómo hacerlo y las particularidades que se presentan.

También te dejo, al final, una advertencia sobre permisos que deberías tener en cuenta.

Vamos allá…

Instalar Docker Desktop for Windows con WSL 2 - Imágenes Linux nativas

WSL es el subsistema Linux de Windows. Gracias a WSL es posible ejecutar nativamente aplicaciones de Linux, e incluso distribuciones completas, dentro de Windows, y sin necesidad de virtualizar o configurar un arranque dual. Es decir, gracias a WSL puedes tener a la vez Windows y Linux funcionando en tu equipo. La versión inicial de WSL, de 2016, no implementaba el Kernel completo de Linux, pero daba bastante margen para trabajar.

En 2020 Microsoft lanzó la versión 2 de la tecnología. WSL 2 cambia por completo la arquitectura, basada en virtualización, y la forma de interactuar entre Windows y las diferentes distribuciones de Linux que podemos instalar en el sistema. WSL 2 proporciona un gran aumento de rendimiento en el sistema de archivos (y por lo tanto en el rendimiento global) y añade soporte total para llamadas del sistema.

Recuerda que Docker Desktop, en sus versiones modernas, puede utilizar WSL 2 para ejecutar nativamente contenedores Linux en Windows, en lugar de usar una máquina virtual Hyper-V (como veremos a continuación para Windows sin WSL 2), lo cual es una gran ventaja. Que use WSL 2 o Hyper-V depende de cómo lo tengas configurado, como verás enseguida.

WSL 2 está disponible en cualquier versión de Windows 10 o posterior cuyo número de build sea igual o superior a 18917. Para ver el número de build de tu instalación de Windows, abre la aplicación de ajustes del sistema y en la opción SistemaAcerca de verás dicho número:

Otra opción es abrir una ventana de línea de comandos (usando cmd.exe, ojo, no PowerShell) y teclear el comando ver.

Si tu versión es superior a 18917 puedes instalar WSL 2 y, por lo tanto, utilizar la integración con Docker Desktop.

Para instalar el subsistema de Linux debes acceder al Panel de Control, buscar por la activación de características de Windows y marcar la opción del subsistema Linux:

Ten en cuenta que ello te instalará también la plataforma para máquinas virtuales (no confundir con Hyper-V ni con la plataforma del hipervisor)

Una vez instalado, deberás habilitar explícitamente WSL 2 desde la línea de comandos:

wsl --set-default-version 2

Este comando establece WSL 2 como la versión por defecto de todas las nuevas distribuciones de Linux que instales, pero si ya tuvieras alguna previa, seguirá con WSL1. Es posible que dicho comando te obligue a instalar una versión actualizada del kernel de Linux que usa WSL 2. Si ese es el caso, se te indicará con un mensaje:

El comando wsl -l -v te muestra las distros Linux instaladas en WSL y en qué versión del subsistema están:

Es posible actualizar una distro de WSL1 a WSL 2 usando wsl --set-version [nombre-distro] 2. Este proceso tarda unos minutos:

Por defecto, la instalación de Docker Desktop detecta que tu sistema dispone de WSL 2 y ya te ofrece la opción de instalar los componentes necesarios (incluso aunque ya los tengas instalados, en cuyo caso no hará nada, y casi que es mejor):

Si lo instalas posteriormente, para usarlo tan solo debes tener una versión de Docker Desktop actualizada y, en Settings, habilitar la opción de usar WSL 2 en la pestaña General (botón derecho sobre el icono de Docker en el área de notificación, y luego Settings):

Una vez que se haya reiniciado Docker Desktop, se habrán creado dos distros WSL adicionales, que son las que usa Docker:

Docker también te da la opción de integrarse con tus distros WSL 2 que ya tuvieses instaladas. Eso es muy interesante ya que te permite compartir las imágenes de Docker entre todas tus distros WSL 2. Y con el propio sistema nativo de Windows, claro, ya que el cliente Windows usa la distro WSL 2 instalada por Docker. Puedes habilitar o deshabilitar esa integración cuando quieras desde Settings, pestaña Resources, opción WSL INTEGRATION:

En la siguiente captura puedes ver ejecutándose a la vez una línea de comandos Windows y mi distro WSL 2 de Ubuntu y cómo, gracias a la integración de Docker, los contenedores e imágenes se comparten, ya que estamos en modo “Contenedores Linux”:

Instalar Docker Desktop for Windows sin WSL 2 - Uso de Máquinas Virtuales Hyper-V

Si tienes una versión de Windows que NO disponga de WSL 2, o no quieres activarla por algún motivo, entonces se va a instalar Hyper-V en tu máquina.

Por cuestiones de licencia, Hyper-V no está soportado en Windows Home, que es la edición que viene con la mayoría de los equipos nuevos, ya que es mucho más barata para el fabricante. No obstante, es muy sencillo poder habilitarla en Windows Home también si sigues estos pasos

Que se instale Hyper-V significa que si quieres utilizar alguna otra tecnología de virtualización en tu máquina, como VirtualBox o VMWare, tendrás que hacer algunos ajustes en Windows, o tendrás un aviso la primera vez que lances Docker o no podrán coexistir Hyper-V y estos otros hipervisores:

En las versiones recientes de Windows existe un componente específico llamado Windows Hypervisor Platform que sirve precisamente para que puedan coexistir varios hipervisores al mismo tiempo en el sistema operativo. Si vas a Panel de ControlProgramas y CaracterísticasActivar o desactivar características de Windows verás la opción disponible, que deberás activar:

Si tu versión de Windows es antigua y no tienes esta opción, entonces no te quedará más remedio que hacer un arranque dual para cambiar de Hyper-V a otros hipervisores, y no podrás usarlos a la vez.

Lo que ocurre al instalar Docker Desktop for Windows es que se instala una máquina virtual en Hyper-V llamada DockerDesktopVM (MobyLinuxVM en versiones más antiguas). Dicha MV contiene una distro de Linux y es la encargada de ejecutar los contenedores. Es decir, si no tienes activado WSL 2, al instalar Docker Desktop en Windows, los contenedores que ejecutamos son siempre contenedores Linux que se ejecutan en una MV. Esto, insisto, es con cualquier versión de Windows que no tenga WSL 2 (soporte o no contenedores nativos de Windows).

Así pues, la situación es la siguiente:

  • Al instalar Docker Desktop en estas versiones de Windows (o si no activas WSL 2) se nos instala una MV Hyper-V (con un Linux) que es la que ejecuta los contenedores y tiene las imágenes.
  • La CLI de Docker se comunica automáticamente con dicha MV. Nosotros no tenemos que hacer nada al respecto. Es transparente, y “es como” si fuese nuestra máquina Windows la que ejecutase los contenedores y tuviese las imágenes.
  • Si nuestra versión de Windows es anterior a Windows Server 2016 o a Windows 10 Anniversary Edition, ese es el único escenario soportado.
  • Si nuestra versión de Windows soporta contenedores nativos de Windows entonces podremos configurar Docker Desktop for Windows para que no use la MV y sea nuestra máquina real Windows la que ejecute los contenedores, como veremos más adelante.

Debemos entender que cuando instalamos Docker Desktop for Windows sin WSL 2, terminamos teniendo dos sistemas Docker independientes:

  • La MV DockerDesktopVM que contiene imágenes Linux y ejecuta contenedores Linux
  • Nuestro ordenador, que contiene imágenes Windows y ejecuta contenedores Windows

En cualquier momento podemos cambiar de entorno, pero no podemos usar los dos a la vez. Y recuerda que son independientes: si te descargas una imagen en Linux, si luego cambias a contenedores Windows esta imagen no la vas a tener (¡igual ni existe!) y viceversa. Cuando cambiamos de Linux a Windows, Docker detiene la MV DockerDesktopVM y la vuelve a encender cuando pasamos de nuevo de Windows a Linux.

Advertencia sobre permisos

Una vez instalado, para que funcione, tu usuario deberá pertenecer al grupo docker-users, un grupo de seguridad especialmente creado para ejecutar Docker. Si intentas ejecutarlo desde una cuenta que no esté en dicho grupo verás una notificación como esta:

En la práctica significa que deberás utilizar Docker con la cuenta de administrador con la que lo has instalado.

Una vez ejecutado como administrador y tras unos segundos de preparación verás una notificación, como esta, informando del éxito:

Coexistencia de contenedores Linux y Windows

Cuando trabajas con Docker en Windows, puedes utilizar contenedores Linux o contenedores Windows. Puedes cambiar de un modo a otro utilizando el menú contextual del icono de Docker en el área de notificación y elegir la opción correspondiente:

Cuando apareció el soporte para WSL 2 en Windows, Docker utilizaba una tecnología llamada LCOW para simultanear contenedores Linux y Windows en la máquina, pero no estaban integrados. Eso significaba que si cambiábamos el modo de Docker a contenedores Windows entonces:

  • Podíamos ejecutar contenedores Windows
  • Podíamos ejecutar contenedores Linux, gracias a LCOW y a las máquinas virtuales
  • Pero Desde WSL no podíamos acceder al daemon de Docker

Por ejemplo, la siguiente captura muestra una línea de comandos de Windows, con dos imágenes Docker en ejecución, una de Windows (mcr.microsoft.com/windows/nanoserver:1903) y otra de linux (node:latest). Recuerda que, en este caso, Docker está configurado para contenedores Windows, pero gracias a LCOW podíamos ejecutar el contenedor de Node.js (y vemos que, en efecto, se ejecuta bajo Linux). Pero, también podemos comprobar cómo desde WSL no era posible acceder al daemon de Docker:

Pero, eso ya no es así: en las versiones modernas de Docker Desktop, si tenemos Docker en modo contenedores Windows:

  • desde un terminal Windows (cmd o powershell) podemos ejecutar contenedores Windows.
  • desde un terminal WSL 2 seguimos viendo nuestros contenedores Linux y podemos seguir operando con ellos.

La imagen anterior muestra dos terminales: arriba un terminal WSL 2 y abajo un terminal Powershell. Tenemos Docker configurado en modo contenedores Windows y tenemos la integración WSL 2 habilitada. Como puedes ver, desde el terminal de WSL 2 manejo mis contenedores Linux y desde el terminal Powershell manejo los contenedores Windows.

Observa como, desde Powershell, intentamos ejecutar alpine (un contenedor Linux) y Docker dice que no encuentra alpine para windows/amd64, mientras que en el terminal WSL 2 sí tenemos alpine listado en la sección de imágenes. También puedes observar que la salida de docker ps (comando que devuelve los contenedores ejecutándose) es distinta: en WSL 2 tenemos un contenedor de adminer, mientras que en Windows no tenemos ninguno ejecutándose.

Es decir, en modo de contenedores Windows, gestionas los contenedores Windows desde PowerShell o una línea de comandos, y los contenedores Linux desde WSL 2. Pero, si tienes configurado Docker para que no use WSL 2, sino la “antigua” MV Hyper-V (como hemos visto), entonces al usar contenedores Windows pierdes todo acceso a los contenedores Linux que tuvieras. No puedes verlos ni gestionarlos desde ningún tipo de terminal hasta que vuelvas al modo de contenedores Linux. Es otra de las “pegas” de no usar la integración con WSL 2.

Para facilitar la comprensión de todo esto, te dejo la siguiente tabla a modo de resumen:

Modo Docker Puedo gestionar contenedores Linux desde… Puedo gestionar contenedores Windows desde…
WSL 2 - Contenedores Linux Terminales Windows (PS/cmd) o terminales WSL 2 Terminales Windows (ver nota)
WSL 2 - Contenedores Windows Terminales WSL 2 y Terminales Windows (ver nota) Terminales Windows (PS/cmd)
HyperV- Contenedores Linux Terminales Windows (PS/cmd) No puedo
HyperV- Contenedores Windows No puedo Terminales Windows (PS/cmd)

Existe una manera de poder manejar, desde terminales WINDOWS (PowerShell y cmd.exe), cualquier tipo de contenedores (ya sea Linux o Windows) con independencia de si Docker Destkop está en modo Windows o Linux. Dado que es una configuración un poco avanzada y hay que activarla manualmente, se discute en el módulo de “Contenedores Windows”.

Instalación de Docker en Linux

En Linux existen dos productos que puedes instalar para trabajar con Docker: Docker Engine (completamente gratuito) y Docker Desktop (sujeto a licencia e incluso a pago según ciertas condiciones).

Docker Engine es el producto “original” y contiene todo lo necesario para crear, administrar y ejecutar contenedores. Se trata de una herramienta de línea de comandos sin ningún tipo de interfaz gráfica. Hace uso directo del soporte de contenedores de Linux y se ejecuta directamente en tu máquina, sin usar ningún tipo de hipervisor.

Docker Engine

Para instalar Docker en Linux debes seguir las instrucciones correspondientes a la distribución de Linux que tengas, ya que varía de una a otra.

Pero, es importante resaltar cómo solucionar un posible problema que se puede dar tras instalarlo. Un error de permisos al ejecutar Docker similar a este:

Este error se da porque tu usuario no tiene permisos para conectarse con el pipe /var/run/docker.sock, que es el mecanismo que utiliza la CLI de Docker para comunicarse con el servidor.

Si lo ejecutas con sudo, te funcionará correctamente:

Por supuesto tener que usar sudo no es lo ideal. Para evitarlo y poder usar Docker sin permisos de root, debes añadir el usuario actual al grupo de usuarios docker. Para ello debes ejecutar el comando:

sudo usermod -aG docker $USER

Una vez hayas ejecutado este comando, debes hacer un logout de la máquina y entrar otra vez, para que se cargue la nueva información de pertenencia al grupo.

Este comando confía en que en la variable $USER está el nombre del usuario actual, lo que suele ser cierto en la mayoría de shells y distros de Linux. Puedes verificar si $USER contiene tu nombre de usuario con el comando echo $USER y la salida debe ser tu nombre de usuario. Si no te aparece puedes añadirlo a mano con el comando USER=<tu-login> (nota que no hay ningún espacio ni antes ni después del símbolo =)

¡Ahora Docker te debería funcionar sin necesidad de usar sudo!

Docker Desktop

Al igual que en MacOS y Windows, en Linux también disponemos de Docker Desktop. En este caso es solo una opción, ya que en Linux es posible instalar Docker Engine solamente, tal y como acabamos de ver). Esto no es posible ni en Windows ni en MacOS, donde Docker Desktop es el único producto que podemos utilizar.

La instalación de Docker Desktop en Linux depende de qué distribución tengas: puedes consultar los pasos en la guía de instalación.

Al igual que ocurre en Windows y en Mac, Docker Desktop en Linux utiliza una máquina virtual (VM) para ejecutar contenedores (concretamente utiliza KVM). Eso te puede sorprender un poco, pues Linux ya tiene soporte de contenedores en el propio sistema operativo, así que, no habría motivo alguno a priori para usar una VM (se pueden ejecutar los contenedores directamente, tal y como hace Docker Engine). Los motivos por los cuales Docker Desktop usa una VM en Linux son los siguientes:

  • Para controlar el SO subyacente: al usar una VM controlada por Docker Desktop, es posible asegurar que todos los usuarios van a tener el mismo SO con la misma versión (especialmente del kernel de Linux), lo que permite a Docker garantizar que todas las funcionalidades funcionan igual para cualquier usuario. También permite a Docker garantizar, en la medida de lo posible, que las características de Docker Desktop serán lo más similar posible en los 3 entornos (Windows, MacOS y Linux).
  • Por seguridad: al ejecutarse los contenedores en el entorno aislado de una VM, cualquier acción maliciosa que un contenedor pudiese realizar se verá limitada.

Si usas Linux no es necesario que te instales Docker Desktop. Si quieres hacerlo, adelante, no hay ningún problema, pero en ningún momento del curso se asume que este deba estar instalado.

Docker Desktop y Docker Engine funcionando a la vez

También puedes tener ambos productos instalados y funcionando a la vez. En este caso, es necesario poder indicarle a la CLI de Docker (el comando docker de la terminal, con el que pasarás largos ratos :-)) qué entorno utilizará. De este modo, cuando lances un comando de Docker, se ejecutará en uno u otro entorno según tus preferencias.

Cuando tienes ambos productos funcionando a la vez, tienes realmente dos entornos de Docker diferentes y cada uno de ellos gestionará sus propios contenedores.

Para indicarle a la CLI sobre qué entorno actuar (si Docker Engine o Docker Desktop) se usa el comando docker context.

Si ejecutas el comando docker context ls te dirá los contextos de Docker que tienes instalados:

  • Si tienes Docker Engine, te aparecerá uno llamado default y cuyo valor de DOCKER ENDPOINT es unix:///var/run/docker.sock.
  • Si tienes Docker Desktop te aparecerá otro llamado desktop-linux con un valor de DOCKER_ENDPOINT parecido a unix:///home/<tu-usuario>/.docker/desktop/docker.sock.

Cuando inicias Docker Desktop, este asigna el contexto desktop-linux como el contexto actual (lo puedes ver porque el comando docker context ls te lo marca con un asterisco), lo que implica que todos los comandos de la CLI de Docker se ejecutarán contra Docker Desktop. Cuando cierras Docker Destkop, el contexto actual se cambia a default por lo que, a partir de ese momento, los comandos de Docker irán contra Docker Engine.

Puedes modificar el contexto actual en cualquier momento usando el comando docker context use <nombre-de-contexto>. Esto te permite ir alternando entre Docker Engine y Docker Desktop sin necesidad de ir abriendo y cerrando este último.

Parar Docker Engine

Si usas Docker Desktop, quizá quieres desactivar Docker Engine para que no consuma recursos o para evitar posibles conflictos. Para ello puedes usar el comando:

sudo systemctl stop docker docker.socket containerd

Este comando detiene Docker Engine, pero es posible que cuando reinicies se ponga en marcha otra vez. Puedes deshabilitarlo de forma definitiva con el siguiente comando:

sudo systemctl disable docker docker.socket containerd

Puedes iniciarlo de nuevo, en cualquier momento, usando el comando:

sudo systemctl start docker docker.socket containerd

Si lo deshabilitaste con disable puedes usar el comando enable para que, de nuevo, se ejecute Docker Engine en cada reinicio:

sudo systemctl enable docker docker.socket containerd

Ten presente que esos comandos pueden depender de la distribución de Linux usada. Los indicados aquí son los más habituales (en distros que usan systemctl).

¿Qué es Docker?

Docker es una herramienta para crear, administrar y ejecutar contenedores. Así, que lo primero que debemos tener claro es, qué entendemos por “contenedor”.

Contenedores como "máquinas virtuales ligeras"

Una comparación típica es comparar un contenedor con una máquina virtual (MV). La siguiente imagen ilustra dicha comparación:

Las semejanzas entre un contenedor y una MV son las siguientes:

  • Ambos proveen un entorno aislado para la ejecución de programas.
  • Ambos pueden moverse entre hosts de forma segura: si una MV o un contenedor se ejecuta correctamente en un host lo hará en todos los demás.

Por eso muchas veces se dice que los contenedores son “máquinas virtuales ligeras”, pero eso dista mucho de la verdad. La realidad es que existen más diferencias que semejanzas entre una MV y un contenedor:

  • Una MV puede ejecutar un SO distinto del que hay en el huésped. Puedo ejecutar Linux en una MV en un host Windows o Mac y viceversa. Técnicamente, cualquier combinación entre sistema operativo host y sistema operativo que ejecuta la MV es posible (otra cosa es que haya algunas restricciones de licencia, como ocurre con MacOS). Por su parte, un contenedor solo puede ejecutar binarios de la misma arquitectura que el sistema operativo host. Es decir, si ejecutamos Docker en Linux, solo vamos a poder ejecutar binarios Linux (y de la misma arquitectura) en los contenedores. Lo mismo ocurre en Windows y en Mac, por supuesto.
  • Una MV ejecuta un SO completo y dentro de ese SO ejecuta varios procesos. Por su parte, un contenedor ejecuta un solo proceso. Cuando ese proceso finaliza, el contenedor “muere” (aunque es cierto que este proceso raíz puede iniciar otros procesos).
  • Efectivamente, tanto MV como contenedores ofrecen un entorno aislado para la ejecución de aplicaciones. Pero, a diferencia de las MV, en los que cada MV tiene toda la infraestructura (memoria, procesador, red, …), los contenedores comparten dicha infraestructura, que es proveída por el host. Por eso, a diferencia de una MV, no vas a establecer “la memoria de un contenedor” o “su tamaño de disco” (aunque sí puedes establecer límites de memoria o CPU).

En definitiva, y a pesar de la comparación, los contenedores no son una tecnología de virtualización. No compiten (ni lo pretenden) con las máquinas virtuales. Juegan un rol distinto.

Contenedores como mecanismo de empaquetamiento de aplicaciones

Dejemos pues de ver los contenedores como un sistema de virtualización y pasemos a verlos como una manera de empaquetar una aplicación y todas sus dependencias. Así, un contenedor es un mecanismo para distribuir una aplicación y todas sus dependencias de forma que dicha aplicación pueda funcionar en cualquier máquina, sin necesidad de que esta tenga instalada nada más que un entorno de ejecución de contenedores, es decir, Docker.

Por supuesto, además de Docker para poder ejecutar los contenedores, el ordenador debe ser del mismo sistema operativo y arquitectura que el contenedor. Así, si empaquetamos en un contenedor una aplicación Linux para x64 lo podremos ejecutar en cualquier distro de Linux que sea x64, pero no en Windows o en Mac. Y si empaquetamos una aplicación para Windows x64 en un contenedor, del mismo modo solo lo podremos ejecutar en sistemas Windows x64.

Cuando empaquetas una aplicación en un contenedor, dicho contenedor contiene la aplicación y todas sus dependencias, es decir:

  • Una copia de la base del SO. Si es una aplicación para Linux, el contenedor contendrá una distro base de Linux. La llamo “base” porque no es necesario que sea una “distro” completa, solo que tenga lo mínimo necesario para poder ejecutar aplicaciones.
  • Una copia de todas las bibliotecas necesarias para tu aplicación. Si tu aplicación depende de foo.so o de bar.dll esos ficheros estarán en el contenedor.
  • El código de tu aplicación, así como cualquier recurso adicional necesario.

Quizá te preguntes cuál es la ventaja de empaquetar aplicaciones en contenedores. Pues, básicamente, asegurar la independencia del contenedor respecto al host. Esto es muy interesante en escenarios con hosts que ejecutan varias aplicaciones.

Por ejemplo, vamos a suponer que tenemos una aplicación web desarrollada en ASP.NET y que depende de .NET Framework 4 en Windows.

Cuando publicamos nuestra aplicación, generamos todos los binarios que luego instalamos en el host. Esos binarios incluyen, no solo nuestra aplicación, sino, generalmente, las bibliotecas asociadas. Es decir, si mi aplicación usa la biblioteca bar.dll dicha biblioteca se copiará como resultado de la publicación de aplicación (nótese que eso no siempre tiene por qué ser así, depende de cada caso en concreto, pero asumamos que es de este modo). Visto así, podríamos pensar que el resultado de la publicación de la aplicación contiene mi aplicación y todas sus dependencias, pero eso no es cierto. En este ejemplo en concreto (aplicación web realizada en ASP.NET) existen al menos dos dependencias que nuestra publicación no incluye (dejando de lado el SO Windows):

  • IIS (Internet Information Server - servidor web utilizado en Windows)
  • .NET Framework 4

Si despliego mi aplicación en un host que no tenga IIS instalado, mi aplicación no va a funcionar. Además, no basta con instalarlo. Debe estar correctamente configurado. Por otro lado, si el host no contiene .NET Framework 4 mi aplicación tampoco va a funcionar.

En principio tampoco parece tan problemático: cualquier host dedicado a hospedar aplicaciones web en Windows tendrá instalado IIS y muy seguramente .NET Framework. Ahora bien, el problema puede venir porque .NET Framework es un “componente de máquina”: hay, por norma general, un solo .NET Framework instalado en cada ordenador (otra vez eso no es cierto siempre, algunas (¡pero no todas!) versiones de .NET Framework pueden coexistir de forma simultánea). Supongamos que tenemos .NET Framework 4.0 instalado en el host, por lo que al desplegar mi aplicación todo funciona correctamente.

Más adelante se quiere desplegar otra aplicación que depende de .NET Framework 4.5. Eso implica tener que instalar .NET Framework 4.5 en el host, lo que supone sustituir .NET Framework 4 por la versión 4.5. Ahora, en el host, hay dos aplicaciones: la primera que depende de .NET Framework 4 y la segunda que lo hace de .NET Framework 4.5. En principio, .NET Framework 4.5 puede ejecutar aplicaciones que dependan de 4.0, pero puede haber algún breaking change que rompa la primera aplicación. En algunos (quizá en muchos) casos todo funcionará bien, pero no tenemos la garantía absoluta. Eso implica que deberíamos probar y asegurar que la primera aplicación (diseñada para .NET Framework 4) funciona bien ejecutándose bajo .NET Framework 4.5. En según qué entornos eso supone una inversión considerable de tiempo y dinero.

¡Y este ha sido un ejemplo sencillo! En general, cualquier recurso que instales a nivel de SO y que puede ser compartido por varias aplicaciones (bibliotecas compartidas en un directorio determinado, ensamblados en la GAC, etc.) puede causar dolores de cabeza en un host compartido.

Insisto, no te quedes en que el ejemplo ha sido en entornos .NET. Imagina, si quieres, un entorno PHP: ¿es la versión de PHP del host compatible con la que has usado para tu aplicación? O piensa un escenario similar en un entorno Java, o NodeJS… la problemática es siempre la misma.

Los contenedores vienen a solucionar este problema: da igual la versión de .NET Framework, o de PHP, o de NodeJS, o de JRE del host, es más: da incluso igual si el host tiene o no instalado .NET o PHP o lo que sea. El contenedor dispone de todo lo necesario para tu aplicación: las bibliotecas base del SO, el entorno concreto que hayas usado y cualquier biblioteca adicional que necesites. No es necesario tener nada instalado ni configurado en el host. Basta que el host pueda ejecutar contenedores, es decir que tenga Docker instalado.

Docker viene a terminar con la conocida situación de “Pero… ¡En mi máquina funciona!”

Lo que es importante recalcar es que, al final, un contenedor es un artefacto binario, que por lo tanto podremos mover y copiar entre hosts.

Otras tecnologías de contenedores

Es importante que conozcas que Docker no es la única tecnología de contenedores disponible, aunque sí es cierto que es la tecnología dominante. Pero, en algunos aspectos, a Docker se le empiezan a ver “las costuras”, incluso a pesar de los esfuerzos que están haciendo para renovarlo (BuildKit es el mejor ejemplo de esos esfuerzos).

En 2015 se creó la OCI (Open Container Initiative), un organismo participado por varias empresas (entre ellas Docker, pero también los grandes “players” como RedHat, IBM o Google) con el objetivo de definir estándares de contenedores, de forma que puedan compartirse contenedores e imágenes creados mediante distintas tecnologías.

Existen varios proyectos de contenedores que creo importante mencionar, para que veas que el mundo de los contenedores no se reduce a Docker:

  • rkt: lo pongo aquí por motivos de completitud, ya que fue la primera gran alternativa a Docker. Vino de la mano de CoreOS (ahora RedHat) y llegó incluso a ser un proyecto incubatorio de la CNCF, pero su desarrollo se ha parado y por lo tanto no es una opción que debas considerar.
  • podman: quizá la alternativa más sugerente a Docker. La ventaja principal con respecto a Docker es que no requiere de ningún daemon, lo que simplifica su arquitectura y le da mucha versatilidad. Por supuesto, las imágenes construidas con Docker son compatibles con podman y viceversa, ya que ambos sistemas son compatibles con OCI. Permite la ejecución no solo de contenedores, sino de otro concepto llamado pod (relacionado con Kubernetes).
  • kaniko: a diferencia de podman y Docker, Kaniko no es un sistema para crear y ejecutar contenedores, sino un sistema para construir imágenes OCI. Está diseñado para ejecutarse en Kubernetes y permitir la ejecución de pipelines de CI/CD que construyan imágenes de contenedores en Kubernetes.
  • buildah: se trata de otro sistema para construir imágenes OCI, al igual que Kaniko. Es de la gente de RedHat: de hecho, al construir una imagen con podman se usa buildah por debajo (de forma transparente). Pero, no es requisito usarlo junto con podman, puedes hacerlo de forma separada, y dado que no requiere daemon es una alternativa muy interesante en determinados escenarios (p. ej. Kubernetes).

Contenedores como mecanismo de empaquetamiento de aplicaciones

Dejemos pues de ver los contenedores como un sistema de virtualización y pasemos a verlos como una manera de empaquetar una aplicación y todas sus dependencias. Así, un contenedor es un mecanismo para distribuir una aplicación y todas sus dependencias de forma que dicha aplicación pueda funcionar en cualquier máquina, sin necesidad de que esta tenga instalada nada más que un entorno de ejecución de contenedores, es decir, Docker.

Cuando empaquetas una aplicación en un contenedor, dicho contenedor contiene la aplicación y todas sus dependencias, es decir:

  • Una copia de la base del SO. Si es una aplicación para Linux, el contenedor contendrá una distro base de Linux. La llamo “base” porque no es necesario que sea una “distro” completa, solo que tenga lo mínimo necesario para poder ejecutar aplicaciones.
  • Una copia de todas las bibliotecas necesarias para tu aplicación. Si tu aplicación depende de foo.so o de bar.dll esos ficheros estarán en el contenedor.
  • El código de tu aplicación, así como cualquier recurso adicional necesario.

Quizá te preguntes cuál es la ventaja de empaquetar aplicaciones en contenedores. Pues, básicamente, asegurar la independencia del contenedor respecto al host. Esto es muy interesante en escenarios con hosts que ejecutan varias aplicaciones.

Lo que es importante recalcar es que, al final, un contenedor es un artefacto binario, que por lo tanto podremos mover y copiar entre hosts.

Otras tecnologías de contenedores

En 2015 se creó la OCI (Open Container Initiative), un organismo participado por varias empresas (entre ellas Docker, pero también los grandes “players” como RedHat, IBM o Google) con el objetivo de definir estándares de contenedores, de forma que puedan compartirse contenedores e imágenes creados mediante distintas tecnologías.

Existen varios proyectos de contenedores que creo importante mencionar, para que veas que el mundo de los contenedores no se reduce a Docker:

  • rkt: lo pongo aquí por motivos de completitud, ya que fue la primera gran alternativa a Docker. Vino de la mano de CoreOS (ahora RedHat) y llegó incluso a ser un proyecto incubatorio de la CNCF, pero su desarrollo se ha parado y por lo tanto no es una opción que debas considerar.
  • podman: quizá la alternativa más sugerente a Docker. La ventaja principal con respecto a Docker es que no requiere de ningún daemon, lo que simplifica su arquitectura y le da mucha versatilidad. Por supuesto, las imágenes construidas con Docker son compatibles con podman y viceversa, ya que ambos sistemas son compatibles con OCI. Permite la ejecución no solo de contenedores, sino de otro concepto llamado pod (relacionado con Kubernetes).
  • kaniko: a diferencia de podman y Docker, Kaniko no es un sistema para crear y ejecutar contenedores, sino un sistema para construir imágenes OCI. Está diseñado para ejecutarse en Kubernetes y permitir la ejecución de pipelines de CI/CD que construyan imágenes de contenedores en Kubernetes.
  • buildah: se trata de otro sistema para construir imágenes OCI, al igual que Kaniko. Es de la gente de RedHat: de hecho, al construir una imagen con podman se usa buildah por debajo (de forma transparente). Pero, no es requisito usarlo junto con podman, puedes hacerlo de forma separada, y dado que no requiere daemon es una alternativa muy interesante en determinados escenarios (p. ej. Kubernetes).

Contenedores y microservicios

Las arquitecturas orientadas a microservicios son una de las tendencias más en boga actualmente. Es importante destacar que el uso de contenedores no implica estar desarrollando en una arquitectura orientada a microservicios y viceversa: se pueden implementar arquitecturas de microservicios sin el uso de contenedores.

Una arquitectura de microservicios requiere que cada microservicio pueda ser desarrollado, desplegado y actualizado de forma independiente. Los contenedores ayudan en los dos últimos puntos al ofrecer un entorno totalmente aislado e independiente en el que empaquetar, desplegar y actualizar nuestro microservicio.

Si usamos contenedores nos independizamos del host que al final ejecutará nuestros microservicios y además, dado que el contenedor contiene todo lo necesario para ejecutar mi aplicación (o microservicio), este se podrá desplegar de forma independiente.

Ahora bien, si usamos una arquitectura monolítica tradicional, también nos podemos beneficiar de los contenedores. Así que resumiendo: aunque los contenedores como mecanismo de despliegue facilitan y encajan muy bien con las necesidades de una arquitectura orientada a microservicios, se pueden usar en muchos otros escenarios. No caigas en el error de pensar que solo grandes arquitecturas distribuidas se benefician de los contenedores. Y tampoco caigas en el error de pensar que sin el uso de contenedores dichas arquitecturas no son posibles. Cualquier tipo de aplicación y de arquitectura se puede beneficiar de los contenedores.

Contenedores e imágenes

Hemos visto someramente qué es Docker y qué entendemos por contenedor. Pero, hemos empleado la palabra “contenedor” un poco a ligera y la hemos usado en algunos contextos en los que no es del todo correcta. La realidad es que debemos distinguir entre “contenedor” e “imagen”.

Haciendo un símil con la POO (Programación Orientada a Objetos) podríamos decir que la relación entre “imagen” y “contenedor” es la misma que hay entre “clase” y “objeto”. Una imagen nos describe los contenidos que tendrá el contenedor, así como su configuración y el proceso que se ejecutará. Mientras que un contenedor es el resultado de ejecutar una imagen.

Las imágenes no se ejecutan, son meras definiciones que contienen todo lo necesario para crear los contenedores. Así, cuando antes dijimos que “un contenedor es un artefacto binario, que por lo tanto podremos mover y copiar entre hosts”, lo que deberíamos haber dicho realmente es que “una imagen es un artefacto binario, que por lo tanto podremos mover y copiar entre hosts”.

Los contenedores tienen un ciclo de vida (básicamente pueden estar ejecutándose o bien pueden haber finalizado su ejecución), mientras que las imágenes no tienen ningún ciclo de vida asociado.

Es importante señalar que solo podemos crear contenedores a partir de imágenes que tengamos descargadas en nuestro sistema y que podemos crear simultáneamente más de un contenedor a partir de la misma imagen.

Registros de imágenes

Para poder crear contenedores, primero necesitamos la imagen correspondiente. Para ello, o bien debemos crearla, o bien la podemos descargar de un registro.

Muchas empresas proporcionan imágenes que podemos descargar y utilizar directamente, y nosotros podemos compartir nuestras propias imágenes de forma pública o privada utilizando un registro.

Es decir, las imágenes nunca se comparten mediante disco o enviando el archivo físico por correo electrónico. Siempre se comparten publicándolas a un registro y luego, descargándolas de dicho registro.

Existen muchos registros de imágenes, pero el registro por defecto es Docker Hub. Podemos usar Docker Hub para:

  • Publicar nuestras propias imágenes para que puedan ser usadas por terceros.
  • Descargar imágenes publicadas por otras personas, empresas u organizaciones.

Más adelante veremos más detalles sobre Docker Hub (y sobre otros registros de imágenes), pero veamos ahora cómo nos podemos descargar nuestra primera imagen.

Usaremos el comando pull para indicar cuál es la imagen que nos queremos descargar. Así que, abre una CLI y teclea:

docker pull hello-world

La salida de dicho comando será algo parecido a:

Using default tag: latest
latest: Pulling from library/hello-world
b04784fba78d: Pull complete
Digest: sha256:f3b3b28a45160805bb16542c9531888519430e9e6d6ffc09d72261b0d26ff74f
Status: Downloaded newer image for hello-world:latest

No te preocupes por esa salida por ahora, más adelante aprenderemos qué significa cada una de esas líneas.

Lo importante es que ahora nos hemos descargado la imagen 'hello-world' y ya la tenemos en nuestro sistema. Y dicha descarga ha sido realizada desde el registro “Docker Hub” que es el que se usa por defecto (más adelante veremos cómo usar otros registros alternativos).

Si quieres crear un contenedor para ejecutar dicha imagen, teclea docker run hello-world. Con ese comando se crea un contenedor nuevo a partir de la imagen hello-world que nos hemos descargado previamente:

Docker Desktop en Windows y error de acceso denegado

En Windows si ejecutas Docker sin permisos de administrador puedes recibir un error como este:

Este error es debido a que Docker Desktop en Windows usa una named pipe llamada \\.\pipe\docker_engine y tu usuario (por la razón que sea) no tiene acceso a dicha pipe. En general, si tu usuario pertenece al grupo docker-users deberías poder ejecutar Docker sin necesidad de permisos administrativos, pero hay un error en algunas versiones de Docker (anteriores a 18.03) que obligan a ejecutarlo desde una línea de comandos administrativa.

Named pipe es un mecanismo del sistema operativo que permite abrir un flujo de comunicación entre dos procesos. Se puede ver como un fichero compartido por dos procesos, en el cual lo que un proceso escribe otro puede leerlo. Existen tanto en Windows como en Unix (aunque más conocidas bajo el nombre de FIFOs).

Como curiosidad puedes ver los permisos asociados a la named pipe tecleando desde una consola de PowerShell:

PS> [System.IO.Directory]::GetAccessControl("\\.\pipe\docker_engine") |  Format-List

Este comando te mostrará la ACL asociada a esta named pipe:

En mi caso, como se observa en la imagen, mi usuario (UFOBOT-V4\etoma) es el propietario de dicha named pipe y hay establecidos permisos para:

  • El usuario NT AUTHORITY\SYSTEM
  • Usuarios del grupo Administrators (es decir, los administradores)
  • Usuarios del grupo docker-users

Si por cualquier motivo el grupo docker-users no está establecido con permisos en la ACL, recibirás el error. Si este es tu caso, lo más sencillo es asegurarte de ejecutarlo siempre desde una línea de comandos con privilegios elevados, o bien, si es posible, actualizar a una versión más moderna de Docker Desktop y verificar si eso resuelve el error.

Error de acceso denegado en Linux

En Linux, si ejecutas el comando anterior, es posible que recibas un error de permisos denegados sobre /var/run/docker.sock. Esta es la named pipe que se usa en Linux y mediante la cual se comunican la herramienta de línea de comandos y el servidor de Docker. Para añadir permisos a tu usuario basta con agregarlo al grupo llamado docker, mediante el comando:

sudo usermod -a -G docker $USER

Luego debes salir de tu sesión (logout) y entrar de nuevo (en caso de dudas: ¡reinicia!) y ya te debería funcionar sin problemas.

Aclarando nomenclatura

Para terminar esta introducción vamos a aclarar un poco de nomenclatura, digamos “comercial” que puedes encontrar. Básicamente para que no te confundas.

En general, en este curso hablaremos de “Docker” sin más distinciones, pero en el fondo “Docker” no es un producto sino una empresa y, según el contexto, es más apropiado utilizar otra terminología más específica.

Así que, a continuación, te facilito un listado con varios nombres y conceptos que seguramente te vas a encontrar cuando leas artículos o noticias sobre Docker y que te conviene tener claros para no equivocarte.

Productos de Docker

  • Docker Engine: se trata de un entorno de desarrollo y ejecución de contenedores basado en línea de comandos. No incluye ninguna herramienta gráfica y está solo disponible para Linux. Es lo que debes instalar si vas a crear, testear, depurar, empaquetar y desplegar contenedores con Docker en este sistema operativo. Usando Docker Engine los contenedores se ejecutan directamente en la máquina host, a diferencia de Docker Desktop que emplea tecnologías de virtualización para ejecutarlos en una máquina virtual.
  • Docker Desktop: producto de Docker que integra Docker Engine, una pequeña interfaz gráfica, herramientas adicionales y soporte para Kubernetes (por lo que te permite crear y depurar despliegues complejos utilizando esta tecnología de orquestación). Es la herramienta que debes instalar en Windows y en Mac (ya que no existe Docker Engine en esos sistemas). En el caso específico de Windows te proporciona la capacidad de poder ejecutar contenedores nativos que trabajan sobre Windows en lugar de sobre *NIX. Si bien su instalación es obligatoria en Windows y en Mac, en Linux es opcional (al existir Docker Engine) y puedes decidir si quieres instalarla o no. Si usas Linux, para seguir el curso basta con Docker Engine. A diferencia de Docker Engine, que es completamente gratuito (y open source), Docker Desktop requiere licencia de pago bajo algunas circunstancias, como ya hemos visto. En cualquier caso, para esta formación puedes instalarlo sin problema.
  • Docker EE (Docker Enterprise Edition): producto ya desaparecido orientado a CaaS (Container as a Service), que permitía hospedar contenedores en una plataforma certificada por la propia empresa Docker. Se trataba de un producto de pago para desplegar tanto en la nube como en los sistemas propios de la empresa. A finales del año 2019 fue adquirido por la empresa Mirantis quienes terminaron convirtiéndolo en lo que ahora se conoce como Mirantis Kubernetes Engine.
  • Docker Toolbox: se trata de un producto obsoleto (la recomendación es usar Docker Desktop), para permitir ejecutar contenedores Linux en MacOS y Windows. Docker Toolbox es para Windows anteriores a Windows 10 y usa VirtualBox como tecnología de virtualización para soportar contenedores Linux. Ninguno de los aspectos más avanzados (como contenedores Windows) está disponible, así que deberías evitarlo.

Componentes básicos de Docker

  • Moby: nombre que se le da actualmente al proyecto open source que es el motor de Docker. La diferencia con Docker Desktop/Engine es que, este último es un producto comercial con más cosas, mientras que Moby es tan solo el motor de Docker. Si tienes interés en personalizar el motor de Docker, en modificar su comportamiento o entender cómo está implementado, ahí es donde debes mirar.
  • containerd: es lo que utiliza Docker desde su versión 1.11 y posteriores como motor de ejecución de contenedores. Moby usa containerd para ejecutar los contenedores. Es una herramienta de muy bajo nivel.
  • runC: herramienta de línea de comandos para lanzar contenedores según la especificación OCI (Open Container Initiative). Se trata de una herramienta de bajo nivel que, en según qué escenarios, es utilizada por containerd.

Es importante que comprendas la relación entre Moby, containerd y runC. Moby es el motor de Docker con el cual interactuamos (a través de la CLI de docker) y que usa containerd para ejecutar y manejar los contenedores. A su vez, para crear y ejecutar los contenedores, containerd lanza y controla varias instancias de runC

  • Docker daemon: conocido también como dockerd sería la “parte servidora” de Docker que se encarga de comunicarse con la CLI y de llevar a cabo las tareas solicitadas por esta. Cuando utilices la interfaz de línea de comandos (CLI) de Docker para gestionar tus contenedores, esta se comunicará con Docker daemon para ello. Es importante notar que el daemon puede estar ejecutándose en otra máquina distinta de la que ejecuta la CLI, lo que nos permite gestionar contenedores de máquinas remotas. Por defecto, la CLI y el daemon se comunican mediante una named pipe, aunque también es posible usar TCP.
  • BuildKit: también conocido como “el docker build de nueva generación”, es la nueva herramienta que usa Docker para construir las imágenes. Si usas una versión reciente de Docker, seguramente lo estás usando sin ser consciente de ello. Tiene varias ventajas respecto al antiguo sistema (cuestiones de rendimiento fundamentalmente), siendo su limitación principal que solo puede construir contenedores Linux. Tienes todos los detalles en la documentación de Docker.

Distribuciones específicas para Docker

  • LinuxKit: distribución minimalista de Linux que contiene fundamentalmente tan solo el Kernel de Linux (aprox. 35MB). El objetivo de LinuxKit es permitir un subsistema de Linux que pueda ejecutar contenedores en entornos muy limitados como escenarios IoT (Internet de las cosas) o similares. No es, por supuesto, una distro Linux de uso general y, además, partes solo del Kernel y tienes que configurarla para cada escenario.
  • Alpine: distribución de Linux pequeña que se usa como base para muchas imágenes de contenedores. No hay que confundirla con LinuxKit, la anterior: Alpine es un Linux de uso general, mientras que LinuxKit no.
informatica/sistemas_operativos/cursos/docker_a_fondo_introduccion_kubernetes/introduccion_docker.1707904276.txt.gz · Última modificación: por tempwin