docker container run
| Descripción | Crea y ejecuta un nuevo contenedor a partir de una imagen |
|---|---|
| Uso | docker container run [OPTIONS] IMAGE [COMMAND] [ARG...] |
| Alias | docker run |
Descripción
El comando docker run ejecuta un comando en un nuevo contenedor, descargando (pull) la imagen si es necesario e iniciando el contenedor.
Puedes reiniciar un contenedor detenido con todos sus cambios anteriores intactos usando docker start.
Usa docker ps -a para ver una lista de todos los contenedores, incluidos los que están detenidos.
Opciones
| Opción | Predeterminado | Descripción |
|---|---|---|
--add-host | Añade una asignación personalizada de host a IP (host:ip) | |
--annotation | API 1.43+
Añade una anotación al contenedor (se pasa al entorno de ejecución OCI) | |
-a, --attach | Se asocia a STDIN, STDOUT o STDERR | |
--blkio-weight | E/S de bloque (peso relativo), entre 10 y 1000, o 0 para desactivar (por defecto 0) | |
--blkio-weight-device | Peso de E/S de bloque (peso relativo del dispositivo) | |
--cap-add | Añade capacidades de Linux | |
--cap-drop | Descarta capacidades de Linux | |
--cgroup-parent | Cgroup primario opcional para el contenedor | |
--cgroupns | API 1.41+
Espacio de nombres cgroup a utilizar (host|private) 'host': Ejecuta el contenedor en el espacio de nombres cgroup del host Docker 'private': Ejecuta el contenedor en su propio espacio de nombres cgroup privado '': Utiliza el espacio de nombres cgroup configurado por la opción default-cgroupns-mode en el demonio (por defecto) | |
--cidfile | Escribe el ID del contenedor en el archivo | |
--cpu-count | Cantidad de CPU (solo Windows) | |
--cpu-percent | Porcentaje de CPU (solo Windows) | |
--cpu-period | Limita el período del programador completamente justo (CFS) de la CPU | |
--cpu-quota | Limita la cuota del programador completamente justo (CFS) de la CPU | |
--cpu-rt-period | API 1.25+ Limita el período en tiempo real de la CPU en microsegundos | |
--cpu-rt-runtime | API 1.25+ Limita el tiempo de ejecución en tiempo real de la CPU en microsegundos | |
-c, --cpu-shares | Cuotas de CPU (peso relativo) | |
--cpus | API 1.25+ Número de CPUs | |
--cpuset-cpus | CPUs en las que se permite la ejecución (0-3, 0,1) | |
--cpuset-mems | Memoria (MEMs) en las que se permite la ejecución (0-3, 0,1) | |
-d, --detach | Ejecuta el contenedor en segundo plano e imprime el ID del contenedor | |
--detach-keys | Invalida la secuencia de teclas para desasociar un contenedor | |
--device | Añade un dispositivo del host al contenedor | |
--device-cgroup-rule | Añade una regla a la lista de dispositivos permitidos del cgroup | |
--device-read-bps | Limita la velocidad de lectura (bytes por segundo) de un dispositivo | |
--device-read-iops | Limita la velocidad de lectura (E/S por segundo) de un dispositivo | |
--device-write-bps | Limita la velocidad de escritura (bytes por segundo) en un dispositivo | |
--device-write-iops | Limita la velocidad de escritura (E/S por segundo) en un dispositivo | |
--dns | Establece servidores DNS personalizados | |
--dns-option | Establece opciones de DNS | |
--dns-search | Establece dominios de búsqueda DNS personalizados | |
--domainname | Nombre de dominio NIS del contenedor | |
--entrypoint | Sobrescribe el ENTRYPOINT por defecto de la imagen | |
-e, --env | Establece variables de entorno | |
--env-file | Lee un archivo de variables de entorno | |
--expose | Expone un puerto o un rango de puertos | |
--gpus | API 1.40+ Dispositivos GPU a añadir al contenedor ('all' para pasar todas las GPUs) | |
--group-add | Añade grupos adicionales a los que unirse | |
--health-cmd | Comando a ejecutar para comprobar la salud | |
--health-interval | Tiempo entre ejecuciones de la comprobación (ms|s|m|h) (por defecto 0s) | |
--health-retries | Fallos consecutivos necesarios para reportar que no es saludable (unhealthy) | |
--health-start-interval | API 1.44+
Tiempo entre ejecuciones de la comprobación durante el período de inicio (ms|s|m|h) (por defecto 0s) | |
--health-start-period | API 1.29+
Período de inicio para que el contenedor se inicialice antes de comenzar la cuenta regresiva de reintentos de salud (ms|s|m|h) (por defecto 0s) | |
--health-timeout | Tiempo máximo permitido para que se ejecute una comprobación (ms|s|m|h) (por defecto 0s) | |
--help | Imprime el uso | |
-h, --hostname | Nombre de host del contenedor | |
--init | API 1.25+
Ejecuta un init dentro del contenedor que reenvía señales y recolecta procesos huérfanos | |
-i, --interactive | Mantiene STDIN abierto incluso si no está asociado | |
--io-maxbandwidth | Límite máximo de ancho de banda de E/S para la unidad del sistema (solo Windows) | |
--io-maxiops | Límite máximo de IOps para la unidad del sistema (solo Windows) | |
--ip | | Dirección IPv4 (por ejemplo, 172.30.100.104) |
--ip6 | | Dirección IPv6 (por ejemplo, 2001:db8::33) |
--ipc | Modo IPC a utilizar | |
--isolation | Tecnología de aislamiento del contenedor | |
-l, --label | Establece metadatos en un contenedor | |
--label-file | Lee un archivo delimitado por líneas de etiquetas | |
--link | Añade un enlace a otro contenedor | |
--link-local-ip | Direcciones IPv4/IPv6 de enlace local (link-local) del contenedor | |
--log-driver | Controlador de registros (logging driver) para el contenedor | |
--log-opt | Opciones del controlador de registros | |
--mac-address | Dirección MAC del contenedor (por ejemplo, 92:d0:c6:0a:29:33) | |
-m, --memory | Límite de memoria | |
--memory-reservation | Límite flexible de memoria (soft limit) | |
--memory-swap | Límite de intercambio (swap) igual a la memoria más el intercambio: '-1' para habilitar intercambio ilimitado | |
--memory-swappiness | -1 | Ajusta la agresividad de intercambio (swappiness) de memoria del contenedor (0 a 100) |
--mount | Asocia un montaje de sistema de archivos al contenedor | |
--name | Asigna un nombre al contenedor | |
--network | Conecta un contenedor a una red | |
--network-alias | Añade un alias de ámbito de red para el contenedor | |
--no-healthcheck | Desactiva cualquier HEALTHCHECK especificado en el contenedor | |
--oom-kill-disable | Desactiva OOM Killer (eliminación por falta de memoria) | |
--oom-score-adj | Ajusta las preferencias OOM del host (-1000 a 1000) | |
--pid | Espacio de nombres PID a utilizar | |
--pids-limit | Ajusta el límite de pids del contenedor (establece -1 para ilimitado) | |
--platform | API 1.32+ Establece la plataforma si el servidor tiene capacidad multiplataforma | |
--privileged | Concede privilegios extendidos a este contenedor | |
-p, --publish | Publica puerto(s) de un contenedor en el host | |
-P, --publish-all | Publica todos los puertos expuestos a puertos aleatorios | |
--pull | missing | Descarga (pull) la imagen antes de ejecutar (always, missing, never) |
-q, --quiet | Suprime la salida de la descarga (pull) | |
--read-only | Monta el sistema de archivos raíz del contenedor como de solo lectura | |
--restart | no | Política de reinicio a aplicar cuando un contenedor finaliza |
--rm | Elimina automáticamente el contenedor y sus volúmenes anónimos asociados cuando finaliza | |
--runtime | Entorno de ejecución (runtime) a utilizar para este contenedor | |
--security-opt | Opciones de seguridad (Security Options) | |
--shm-size | Tamaño de /dev/shm | |
--sig-proxy | true | Redirige las señales recibidas al proceso |
--stop-signal | Señal para detener el contenedor | |
--stop-timeout | API 1.25+ Tiempo de espera (en segundos) para detener un contenedor | |
--storage-opt | Opciones del controlador de almacenamiento para el contenedor | |
--sysctl | Opciones de sysctl | |
--tmpfs | Monta un directorio tmpfs | |
-t, --tty | Asigna un pseudo-TTY | |
--ulimit | Opciones de ulimit | |
--use-api-socket | Monta mediante bind el socket de la API de Docker y la autenticación requerida | |
-u, --user | Nombre de usuario o UID (formato: <nombre|uid>[:<grupo|gid>]) | |
--userns | Espacio de nombres de usuario a utilizar | |
--uts | Espacio de nombres UTS a utilizar | |
-v, --volume | Monta un volumen mediante bind mount | |
--volume-driver | Controlador de volúmenes opcional para el contenedor | |
--volumes-from | Monta volúmenes desde el/los contenedor(es) especificado(s) | |
-w, --workdir | Directorio de trabajo dentro del contenedor |
Ejemplos
Asignar nombre (--name)
El flag --name te permite especificar un identificador personalizado para un contenedor. El
siguiente ejemplo ejecuta un contenedor llamado test utilizando la imagen nginx:alpine
en modo desasociado (detached).
$ docker run --name test -d nginx:alpine
4bed76d3ad428b889c56c1ecc2bf2ed95cb08256db22dc5ef5863e1d03252a19
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
4bed76d3ad42 nginx:alpine "/docker-entrypoint.…" 1 second ago Up Less than a second 80/tcp test
Puedes hacer referencia al contenedor por su nombre con otros comandos. Por ejemplo, los
siguientes comandos detienen y eliminan un contenedor llamado test:
$ docker stop test
test
$ docker rm test
test
Si no especificas un nombre personalizado con el flag --name, el demonio asigna
un nombre generado aleatoriamente, como vibrant_cannon, al contenedor. Usar un
nombre definido de forma personalizada ofrece la ventaja de tener un identificador fácil de recordar para el
contenedor.
Además, si conectas el contenedor a una red bridge definida por el usuario, otros contenedores en la misma red pueden referirse a él por su nombre a través de DNS.
$ docker network create mynet
cb79f45948d87e389e12013fa4d969689ed2c3316985dd832a43aaec9a0fe394
$ docker run --name test --net mynet -d nginx:alpine
58df6ecfbc2ad7c42d088ed028d367f9e22a5f834d7c74c66c0ab0485626c32a
$ docker run --net mynet busybox:latest ping test
PING test (172.18.0.2): 56 data bytes
64 bytes from 172.18.0.2: seq=0 ttl=64 time=0.073 ms
64 bytes from 172.18.0.2: seq=1 ttl=64 time=0.411 ms
64 bytes from 172.18.0.2: seq=2 ttl=64 time=0.319 ms
64 bytes from 172.18.0.2: seq=3 ttl=64 time=0.383 ms
...
Capturar el ID del contenedor (--cidfile)
Para ayudar con la automatización, puedes hacer que Docker escriba el ID del contenedor en un archivo de tu elección. Esto es similar a cómo algunos programas escriben su ID de proceso en un archivo (es posible que los conozcas como archivos PID):
$ docker run --cidfile /tmp/docker_test.cid ubuntu echo "test"
Esto crea un contenedor e imprime test en la consola. El flag cidfile
hace que Docker intente crear un nuevo archivo y escriba el ID del contenedor en él.
Si el archivo ya existe, Docker devuelve un error. Docker cierra este
archivo cuando docker run finaliza.
Ajustes de PID (--pid)
--pid="" : Establece el modo de espacio de nombres PID (Proceso) para el contenedor,
'container:<name|id>': se une al espacio de nombres PID de otro contenedor
'host': utiliza el espacio de nombres PID del host dentro del contenedorPor defecto, todos los contenedores tienen activado el espacio de nombres PID.
El espacio de nombres PID proporciona separación de procesos. El espacio de nombres PID elimina la vista de los procesos del sistema y permite reutilizar los IDs de proceso, incluido el PID 1.
En ciertos casos, deseas que tu contenedor comparta el espacio de nombres de procesos del host,
lo que permite a los procesos del contenedor ver todos los procesos del
sistema. Por ejemplo, podrías construir un contenedor con herramientas de depuración como
strace o gdb, pero querer usar estas herramientas para depurar procesos dentro del
contenedor.
Ejemplo: ejecutar htop dentro de un contenedor
Para ejecutar htop en un contenedor que comparte el espacio de nombres de procesos del host:
Ejecuta un contenedor alpine con la opción
--pid=host:$ docker run --rm -it --pid=host alpineInstala
htopen el contenedor:/ # apk add --quiet htopInvoca el comando
htop./ # htop
Ejemplo: unirse al espacio de nombres PID de otro contenedor
Unirse al espacio de nombres PID de otro contenedor puede ser útil para depurar dicho contenedor.
Inicia un contenedor que ejecute un servidor Nginx:
$ docker run --rm --name my-nginx -d nginx:alpineEjecuta un contenedor Alpine que asocie el espacio de nombres
--pidal contenedormy-nginx:$ docker run --rm -it --pid=container:my-nginx \ --cap-add SYS_PTRACE \ --security-opt seccomp=unconfined \ alpineInstala
straceen el contenedor Alpine:/ # apk add straceAsóciate al proceso 1, el ID de proceso del contenedor
my-nginx:/ # strace -p 1 strace: Process 1 attached
Desactivar el remapeo de espacios de nombres para un contenedor (--userns)
Si habilitas los espacios de nombres de usuario (user namespaces) en el demonio,
todos los contenedores se iniciarán con los espacios de nombres de usuario activados por defecto.
Para desactivar el remapeo de espacios de nombres de usuario para un contenedor específico,
puedes establecer el flag --userns en host.
docker run --userns=host hello-world
host es el único valor válido para el flag --userns.
Para más información, consulta Aislar contenedores con espacios de nombres de usuario.
Ajustes de UTS (--uts)
--uts="" : Establece el modo de espacio de nombres UTS para el contenedor
'host': utiliza el espacio de nombres UTS del host dentro del contenedorEl espacio de nombres UTS sirve para establecer el nombre de host y el dominio que es visible para
los procesos en ejecución en ese espacio de nombres. Por defecto, todos los contenedores, incluidos
aquellos con --network=host, tienen su propio espacio de nombres UTS. Establecer --uts en
host hace que el contenedor utilice el mismo espacio de nombres UTS que el host.
NoteDocker no permite combinar los flags
--hostnamey--domainnamecon--uts=host. Esto es para evitar que los contenedores que se ejecutan en el espacio de nombres UTS del host intenten cambiar la configuración de este.
Es posible que desees compartir el espacio de nombres UTS con el host si quieres que el nombre de host del contenedor cambie a medida que cambia el nombre de host del host. Un caso de uso más avanzado sería cambiar el nombre de host del host desde un contenedor.
Ajustes de IPC (--ipc)
--ipc="MODE" : Establece el modo IPC para el contenedorEl flag --ipc acepta los siguientes valores:
| Valor | Descripción |
|---|---|
| "" | Utiliza el valor predeterminado del demonio. |
| "none" | Espacio de nombres IPC propio y privado, con /dev/shm sin montar. |
| "private" | Espacio de nombres IPC propio y privado. |
| "shareable" | Espacio de nombres IPC propio y privado, con posibilidad de compartirlo con otros contenedores. |
| "container:<nombre-o-ID>" | Se une al espacio de nombres IPC de otro contenedor ("compartible"). |
| "host" | Utiliza el espacio de nombres IPC del sistema host. |
Si no se especifica, se utiliza el valor predeterminado del demonio, que puede ser "private"
o "shareable", dependiendo de la versión y configuración del demonio.
Los espacios de nombres de comunicación entre procesos (IPC) de System V proporcionan separación de segmentos de memoria compartida con nombre, semáforos y colas de mensajes.
Los segmentos de memoria compartida se utilizan para acelerar la comunicación entre procesos a la
velocidad de la memoria, en lugar de a través de tuberías o de la pila de red. La memoria compartida
se utiliza habitualmente en bases de datos y aplicaciones de alto rendimiento personalizadas
(típicamente C/OpenMPI, C++/usando bibliotecas boost) para computación científica
e industrias de servicios financieros. Si este tipo de aplicaciones
se dividen en múltiples contenedores, es posible que necesites compartir los mecanismos IPC
de los contenedores, utilizando el modo "shareable" para el contenedor principal (es decir, "donante")
y "container:<donante-nombre-o-ID>" para los demás contenedores.
Escalar privilegios del contenedor (--privileged)
El flag --privileged concede las siguientes capacidades a un contenedor:
- Habilita todas las capacidades del kernel de Linux
- Desactiva el perfil seccomp predeterminado
- Desactiva el perfil AppArmor predeterminado
- Desactiva la etiqueta de proceso SELinux
- Concede acceso a todos los dispositivos del host
- Permite la lectura y escritura en
/sys - Permite la lectura y escritura en los montajes de cgroups
En otras palabras, el contenedor puede hacer casi todo lo que el host puede hacer. Este flag existe para permitir casos de uso especiales, como ejecutar Docker dentro de Docker.
WarningUtiliza el flag
--privilegedcon precaución. Un contenedor con--privilegedno es un proceso aislado de forma segura. Los contenedores en este modo pueden obtener una shell de root en el host y tomar el control del sistema.Para la mayoría de los casos de uso, este flag no debería ser la solución preferida. Si tu contenedor requiere privilegios escalados, deberías preferir otorgar explícitamente los permisos necesarios, por ejemplo, añadiendo capacidades individuales del kernel con
--cap-add.Para más información, consulta Privilegios en tiempo de ejecución y capacidades de Linux
El siguiente ejemplo no funciona porque, por defecto, Docker descarta la mayoría de las
capacidades del kernel potencialmente peligrosas, incluida CAP_SYS_ADMIN (que se
requiere para montar sistemas de archivos).
$ docker run -t -i --rm ubuntu bash
root@bc338942ef20:/# mount -t tmpfs none /mnt
mount: permission denied
Funciona cuando añades el flag --privileged:
$ docker run -t -i --privileged ubuntu bash
root@50e3f57e16e6:/# mount -t tmpfs none /mnt
root@50e3f57e16e6:/# df -h
Filesystem Size Used Avail Use% Mounted on
none 1.9G 0 1.9G 0% /mnt
Establecer el directorio de trabajo (-w, --workdir)
$ docker run -w /path/to/dir/ ubuntu pwd
La opción -w ejecuta el comando especificado dentro del directorio indicado, en este ejemplo,
/path/to/dir/. Si la ruta no existe, Docker la crea dentro del contenedor.
Establecer opciones del controlador de almacenamiento por contenedor (--storage-opt)
$ docker run -it --storage-opt size=120G fedora /bin/bash
Esto (size) limita el tamaño del sistema de archivos del contenedor a 120G en el momento de la creación.
Esta opción solo está disponible para los controladores de almacenamiento btrfs, overlay2, windowsfilter
y zfs.
Para el controlador de almacenamiento overlay2, la opción de tamaño solo está disponible si el
sistema de archivos subyacente es xfs y está montado con la opción de montaje pquota.
Bajo estas condiciones, puedes pasar cualquier tamaño inferior al del sistema de archivos subyacente.
Para los controladores de almacenamiento windowsfilter, btrfs y zfs, no puedes pasar un
tamaño inferior al Default BaseFS Size.
Montar tmpfs (--tmpfs)
El flag --tmpfs te permite crear un montaje tmpfs.
Las opciones que puedes pasar a --tmpfs son idénticas al comando de Linux mount -t tmpfs -o.
El siguiente ejemplo monta un tmpfs vacío en el contenedor con las opciones rw, noexec,
nosuid y size=65536k.
$ docker run -d --tmpfs /run:rw,noexec,nosuid,size=65536k my_image
Para más información, consulta Montajes tmpfs.
Montar volumen (-v)
$ docker run -v $(pwd):$(pwd) -w $(pwd) -i -t ubuntu pwd
El ejemplo anterior monta el directorio actual en el contenedor en la misma ruta
utilizando el flag -v, lo establece como directorio de trabajo y luego ejecuta el comando pwd dentro del contenedor.
A partir de la versión 23 de Docker Engine, puedes utilizar rutas relativas en el host.
$ docker run -v ./content:/content -w /content -i -t ubuntu pwd
El ejemplo anterior monta el directorio content del directorio actual en el contenedor en la
ruta /content utilizando el flag -v, lo establece como directorio de trabajo y luego
ejecuta el comando pwd dentro del contenedor.
$ docker run -v /doesnt/exist:/foo -w /foo -i -t ubuntu bash
Cuando el directorio del host de un volumen montado mediante bind no existe, Docker
lo crea automáticamente en el host por ti. En el ejemplo anterior,
Docker crea la carpeta /doesnt/exist antes de iniciar el contenedor.
Montar volumen como solo lectura (--read-only)
$ docker run --read-only -v /icanwrite busybox touch /icanwrite/here
Puedes utilizar volúmenes en combinación con el flag --read-only para controlar dónde
escribe archivos un contenedor. El flag --read-only monta el sistema de archivos raíz del
contenedor como de solo lectura, prohibiendo la escritura en ubicaciones distintas de los
volúmenes especificados para el contenedor.
$ docker run -t -i -v /var/run/docker.sock:/var/run/docker.sock -v /path/to/static-docker-binary:/usr/bin/docker busybox sh
Al montar mediante bind el socket Unix de Docker y el binario de Docker enlazado estáticamente (consulta obtener el binario de Linux), concedes al contenedor acceso completo para crear y manipular el demonio de Docker del host.
En Windows, debes especificar las rutas utilizando la semántica de rutas estilo Windows.
PS C:\> docker run -v c:\foo:c:\dest microsoft/nanoserver cmd /s /c type c:\dest\somefile.txt
Contents of file
PS C:\> docker run -v c:\foo:d: microsoft/nanoserver cmd /s /c type d:\somefile.txt
Contents of fileLos siguientes ejemplos fallan al utilizar contenedores basados en Windows, ya que el
destino de un volumen o montaje bind dentro del contenedor debe ser uno de los siguientes:
un directorio inexistente o vacío; o una unidad distinta de C:. Además, el origen
de un montaje bind debe ser un directorio local, no un archivo.
net use z: \\remotemachine\share
docker run -v z:\foo:c:\dest ...
docker run -v \\uncpath\to\directory:c:\dest ...
docker run -v c:\foo\somefile.txt:c:\dest ...
docker run -v c:\foo:c: ...
docker run -v c:\foo:c:\existing-directory-with-contents ...Para información detallada sobre volúmenes, consulta Administrar datos en contenedores.
Añadir montajes bind o volúmenes utilizando el flag --mount
El flag --mount te permite montar volúmenes, directorios del host y montajes tmpfs
en un contenedor.
El flag --mount admite la mayoría de las opciones compatibles con -v o el
flag --volume, pero utiliza una sintaxis diferente. Para información detallada sobre el
flag --mount y una comparación entre --volume y --mount, consulta
Montajes bind.
Aunque no hay planes para declarar obsoleto --volume, se recomienda el uso de --mount.
Ejemplos:
$ docker run --read-only --mount type=volume,target=/icanwrite busybox touch /icanwrite/here
$ docker run -t -i --mount type=bind,src=/data,dst=/data busybox sh
Publicar o exponer puerto (-p, --expose)
$ docker run -p 127.0.0.1:80:8080/tcp nginx:alpine
Esto vincula el puerto 8080 del contenedor al puerto TCP 80 en 127.0.0.1 del
host. También puedes especificar puertos udp y sctp. La
página de descripción general de
redes explica detalladamente cómo publicar puertos
con Docker.
NoteSi no especificas una dirección IP (es decir,
-p 80:80en lugar de-p 127.0.0.1:80:80) al publicar los puertos de un contenedor, Docker publica el puerto en todas las interfaces (dirección0.0.0.0) por defecto. Estos puertos son accesibles externamente. Esto también se aplica si configuraste UFW para bloquear este puerto específico, ya que Docker administra sus propias reglas de iptables. Leer más
$ docker run --expose 80 nginx:alpine
Esto expone el puerto 80 del contenedor sin publicar el puerto en las interfaces del sistema
host.
Publicar todos los puertos expuestos (-P, --publish-all)
$ docker run -P nginx:alpine
El flag -P, o --publish-all, publica todos los puertos expuestos en el host.
Docker vincula cada puerto expuesto a un puerto aleatorio en el host.
El flag -P solo publica puertos que están explícitamente marcados como
expuestos, ya sea mediante la instrucción EXPOSE del Dockerfile o el flag --expose
del comando docker run.
El rango de puertos se encuentra dentro de un rango de puertos efímeros definido por
/proc/sys/net/ipv4/ip_local_port_range. Utiliza el flag -p para mapear explícitamente un
solo puerto o rango de puertos.
Establecer la política de descarga (--pull)
Utiliza el flag --pull para establecer la política de descarga de la imagen al crear (y ejecutar)
el contenedor.
El flag --pull puede tomar uno de estos valores:
| Valor | Descripción |
|---|---|
missing (por defecto) | Descarga la imagen si no se encuentra en la caché de imágenes, o utiliza la imagen en caché en caso contrario. |
never | No descarga la imagen, incluso si no se encuentra, y produce un error si la imagen no existe en la caché de imágenes. |
always | Siempre realiza una descarga (pull) antes de crear el contenedor. |
Al crear (y ejecutar) un contenedor a partir de una imagen, el demonio comprueba si la imagen existe en la caché de imágenes local. Si falta la imagen, se devuelve un error a la CLI, lo que le permite iniciar una descarga.
El valor predeterminado (missing) consiste en descargar únicamente la imagen si no está presente en la
caché de imágenes del demonio. Este valor predeterminado te permite ejecutar imágenes que solo existen
localmente (por ejemplo, imágenes que construiste a partir de un Dockerfile pero que no se han
subido a un registro), y reduce el uso de la red.
La opción always siempre inicia una descarga antes de crear el contenedor. Esta
opción garantiza que la imagen esté actualizada y evita que utilices imágenes
obsoletas, pero puede no ser adecuada en situaciones en las que deseas probar una imagen
construida localmente antes de subirla (ya que descargar la imagen sobrescribe la imagen existente
en la caché de imágenes).
La opción never desactiva la descarga (implícita) de imágenes al crear contenedores,
y solo utiliza imágenes que están disponibles en la caché de imágenes. Si la imagen especificada
no se encuentra, se produce un error y el contenedor no se crea.
Esta opción es útil en situaciones en las que la red no está disponible, o para
evitar que las imágenes se descarguen implícitamente al crear contenedores.
El siguiente ejemplo muestra docker run con la opción --pull=never configurada,
lo que produce un error ya que la imagen no se encuentra en la caché de imágenes:
$ docker run --pull=never hello-world
docker: Error response from daemon: No such image: hello-world:latest.
Establecer variables de entorno (-e, --env, --env-file)
$ docker run -e MYVAR1 --env MYVAR2=foo --env-file ./env.list ubuntu bash
Utiliza los flags -e, --env y --env-file para establecer variables de
entorno simples (no de matriz) en el contenedor que estás ejecutando, o sobrescribir variables
definidas en el Dockerfile de la imagen que estás ejecutando.
Puedes definir la variable y su valor al ejecutar el contenedor:
$ docker run --env VAR1=value1 --env VAR2=value2 ubuntu env | grep VAR
VAR1=value1
VAR2=value2
También puedes utilizar variables exportadas a tu entorno local:
export VAR1=value1
export VAR2=value2
$ docker run --env VAR1 --env VAR2 ubuntu env | grep VAR
VAR1=value1
VAR2=value2
Al ejecutar el comando, el cliente CLI de Docker comprueba el valor que tiene la variable
en tu entorno local y lo pasa al contenedor.
Si no se proporciona un = y esa variable no está exportada en tu entorno
local, la variable no se define (unset) en el contenedor.
También puedes cargar las variables de entorno desde un archivo. Este archivo debe utilizar
la sintaxis <variable>=value (que establece la variable al valor dado) o
<variable> (que toma el valor del entorno local), y # para
los comentarios. Las líneas que comienzan con # se tratan como comentarios de línea y se
ignoran, mientras que un # que aparece en cualquier otro lugar de una línea se trata como parte de
la variable.
$ cat env.list
# This is a comment
VAR1=value1
VAR2=value2
USER
$ docker run --env-file env.list ubuntu env | grep -E 'VAR|USER'
VAR1=value1
VAR2=value2
USER=jonzeolla
Establecer metadatos en el contenedor (-l, --label, --label-file)
Una etiqueta es un par key=value que aplica metadatos a un contenedor. Para etiquetar un contenedor con dos etiquetas:
$ docker run -l my-label --label com.example.foo=bar ubuntu bash
La clave my-label no especifica un valor, por lo que la etiqueta toma por defecto una cadena vacía
(""). Para añadir varias etiquetas, repite el flag de etiqueta (-l o --label).
El par key=value debe ser único para evitar sobrescribir el valor de la etiqueta. Si
especificas etiquetas con claves idénticas pero valores diferentes, cada valor posterior
sobrescribe el anterior. Docker utiliza el último par key=value que proporciones.
Utiliza el flag --label-file para cargar varias etiquetas desde un archivo. Delimita cada
etiqueta en el archivo con una marca de fin de línea. El siguiente ejemplo carga etiquetas desde un
archivo de etiquetas en el directorio actual:
$ docker run --label-file ./labels ubuntu bash
El formato del archivo de etiquetas es similar al formato para cargar variables de entorno. (A diferencia de las variables de entorno, las etiquetas no son visibles para los procesos que se ejecutan dentro del contenedor). El siguiente ejemplo muestra el formato de un archivo de etiquetas:
com.example.label1="a label"
# this is a comment
com.example.label2=another\ label
com.example.label3
Puedes cargar varios archivos de etiquetas proporcionando múltiples flags --label-file.
Para información adicional sobre cómo trabajar con etiquetas, consulta Etiquetas.
Conectar un contenedor a una red (--network)
Para iniciar un contenedor y conectarlo a una red, utiliza la opción --network.
Si deseas añadir un contenedor en ejecución a una red, utiliza el subcomando docker network connect.
Puedes conectar varios contenedores a la misma red. Una vez conectados, los
contenedores pueden comunicarse utilizando únicamente la dirección IP o el nombre de otro contenedor.
Para redes de tipo overlay o complementos personalizados que admiten conectividad
multihost, los contenedores conectados a la misma red multihost pero iniciados
desde diferentes motores también pueden comunicarse de esta manera.
NoteLa red bridge predeterminada solo permite que los contenedores se comuniquen entre sí utilizando direcciones IP internas. Las redes bridge creadas por el usuario proporcionan resolución DNS entre contenedores utilizando los nombres de los contenedores.
Puedes desconectar un contenedor de una red utilizando el comando docker network disconnect.
Los siguientes comandos crean una red llamada my-net y añaden un contenedor busybox
a la red my-net.
$ docker network create my-net
$ docker run -itd --network=my-net busybox
También puedes elegir las direcciones IP para el contenedor con los flags --ip y --ip6
cuando inicias el contenedor en una red definida por el usuario. Para asignar una
IP estática a los contenedores, debes especificar el bloque de subred para la red.
$ docker network create --subnet 192.0.2.0/24 my-net
$ docker run -itd --network=my-net --ip=192.0.2.69 busybox
Para conectar el contenedor a más de una red, repite la opción --network.
$ docker network create --subnet 192.0.2.0/24 my-net1
$ docker network create --subnet 192.0.3.0/24 my-net2
$ docker run -itd --network=my-net1 --network=my-net2 busybox
Para especificar opciones al conectarse a más de una red, utiliza la sintaxis extendida
para el flag --network. Las opciones separadas por comas que se pueden especificar en la sintaxis
extendida --network son:
| Oportunidad | Equivalente de nivel superior | Descripción |
|---|---|---|
name | El nombre de la red (obligatorio) | |
alias | --network-alias | Añade un alias de ámbito de red para el contenedor |
ip | --ip | Dirección IPv4 (por ejemplo, 172.30.100.104) |
ip6 | --ip6 | Dirección IPv6 (por ejemplo, 2001:db8::33) |
mac-address | --mac-address | Dirección MAC del contenedor (por ejemplo, 92:d0:c6:0a:29:33) |
link-local-ip | --link-local-ip | Direcciones de enlace local (link-local) IPv4/IPv6 del contenedor |
driver-opt | docker network connect --driver-opt | Opciones del controlador de red |
gw-priority | La prioridad de puerta de enlace (gw-priority) más alta proporciona la puerta de enlace predeterminada. Acepta valores positivos y negativos. |
$ docker network create --subnet 192.0.2.0/24 my-net1
$ docker network create --subnet 192.0.3.0/24 my-net2
$ docker run -itd --network=name=my-net1,ip=192.0.2.42 --network=name=my-net2,ip=192.0.3.42 busybox
Los ajustes de sysctl que comienzan con net.ipv4., net.ipv6. o net.mpls. se pueden
establecer por interfaz utilizando la etiqueta de driver-opt com.docker.network.endpoint.sysctls.
El nombre de la interfaz debe ser la cadena IFNAME.
To set more than one sysctl for an interface, quote the whole driver-opt field,
remembering to escape the quotes for the shell if necessary. For example, if the
interface to my-net is given name eth0, the following example sets sysctls
net.ipv4.conf.eth0.log_martians=1 and net.ipv4.conf.eth0.forwarding=0, and
assigns the IPv4 address 192.0.2.42.
$ docker network create --subnet 192.0.2.0/24 my-net
$ docker run -itd --network=name=my-net,\"driver-opt=com.docker.network.endpoint.sysctls=net.ipv4.conf.IFNAME.log_martians=1,net.ipv4.conf.IFNAME.forwarding=0\",ip=192.0.2.42 busybox
NoteLos controladores de red pueden restringir los ajustes de sysctl que se pueden modificar y, para proteger el funcionamiento de la red, es posible que se añadan nuevas restricciones en el futuro.
Para más información sobre cómo conectar un contenedor a una red al utilizar el comando run,
consulta la
descripción general de redes de Docker.
Montar volúmenes desde un contenedor (--volumes-from)
$ docker run --volumes-from 777f7dc92da7 --volumes-from ba8c0c54f0f2:ro -i -t ubuntu pwd
El flag --volumes-from monta todos los volúmenes definidos desde los contenedores
referenciados. Puedes especificar más de un contenedor repitiendo el argumento
--volumes-from. El ID del contenedor puede tener opcionalmente el sufijo :ro o :rw para
montar los volúmenes en modo de solo lectura o lectura-escritura, respectivamente. Por defecto,
Docker monta los volúmenes en el mismo modo (lectura-escritura o solo lectura) que el
contenedor de referencia.
Los sistemas de etiquetado como SELinux requieren colocar etiquetas adecuadas en el contenido de los volúmenes montados en un contenedor. Sin una etiqueta, el sistema de seguridad podría impedir que los procesos que se ejecutan dentro del contenedor utilicen el contenido. Por defecto, Docker no cambia las etiquetas establecidas por el sistema operativo.
Para cambiar la etiqueta en el contexto del contenedor, puedes añadir uno de los dos sufijos
:z o :Z al montaje del volumen. Estos sufijos indican a Docker que vuelva a etiquetar los objetos de
archivo en los volúmenes compartidos. La opción z indica a Docker que dos contenedores
comparten el contenido del volumen. Como resultado, Docker etiqueta el contenido con una etiqueta de
contenido compartido. Las etiquetas de volúmenes compartidos permiten que todos los contenedores lean y escriban el contenido.
La opción Z indica a Docker que etiquete el contenido con una etiqueta privada no compartida.
Únicamente el contenedor actual puede utilizar un volumen privado.
Modo desasociado (Detached) (-d, --detach)
El flag --detach (o -d) inicia un contenedor como un proceso en segundo plano que
no ocupa tu ventana de terminal. Por diseño, los contenedores iniciados en modo desasociado
finalizan cuando el proceso raíz utilizado para ejecutar el contenedor finaliza, a menos que
también especifiques la opción --rm. Si utilizas -d con --rm, el contenedor se
elimina cuando finaliza o cuando el demonio finaliza, lo que ocurra primero.
No pases un comando service x start a un contenedor desasociado. Por ejemplo,
este comando intenta iniciar el servicio nginx.
$ docker run -d -p 80:80 my_image service nginx start
Esto logra iniciar el servicio nginx dentro del contenedor. Sin embargo,
falla en el paradigma del contenedor desasociado ya que el proceso raíz (service nginx start) finaliza y el contenedor desasociado se detiene como está diseñado. Como resultado, el
servicio nginx se inicia pero no se puede utilizar. En su lugar, para iniciar un proceso como
el servidor web nginx haz lo siguiente:
$ docker run -d -p 80:80 my_image nginx -g 'daemon off;'
Para realizar operaciones de entrada/salida con un contenedor desasociado, utiliza conexiones de red o
volúmenes compartidos. Estos son necesarios porque el contenedor ya no está escuchando en la
línea de comandos donde se ejecutó docker run.
Invalidar la secuencia de desasociación (--detach-keys)
Utiliza la opción --detach-keys para invalidar la secuencia de teclas de Docker para desasociar.
Esto es útil si la secuencia predeterminada de Docker entra en conflicto con la secuencia de teclas que
utilizas para otras aplicaciones. Hay dos formas de definir tu propia secuencia de teclas de
desasociación: como una invalidación por contenedor o como una propiedad de configuración en toda tu
configuración.
Para invalidar la secuencia para un contenedor individual, utiliza el flag
--detach-keys="<secuencia>" con el comando docker attach. El formato de la
<secuencia> es una letra [a-Z] o ctrl- combinado con cualquiera de
los siguientes:
a-z(un solo carácter alfabético en minúscula)@(arroba)[(corchete izquierdo)\\(dos barras invertidas)_(guion bajo)^(circunflejo)
Los valores a, ctrl-a, X o ctrl-\\ son ejemplos de secuencias de teclas
válidas. Para configurar una secuencia de teclas predeterminada diferente para todos los
contenedores, consulta la
sección del archivo de configuración.
Añadir un dispositivo del host al contenedor (--device)
$ docker run -it --rm \
--device=/dev/sdc:/dev/xvdc \
--device=/dev/sdd \
--device=/dev/zero:/dev/foobar \
ubuntu ls -l /dev/{xvdc,sdd,foobar}
brw-rw---- 1 root disk 8, 2 Feb 9 16:05 /dev/xvdc
brw-rw---- 1 root disk 8, 3 Feb 9 16:05 /dev/sdd
crw-rw-rw- 1 root root 1, 5 Feb 9 16:05 /dev/foobar
A menudo es necesario exponer directamente dispositivos a un contenedor. La opción --device
lo permite. Por ejemplo, añadir un dispositivo de almacenamiento de bloques específico, un dispositivo de
bucle (loop) o un dispositivo de audio a un contenedor que de otro modo no tendría privilegios
(sin el flag --privileged) y hacer que la aplicación acceda directamente a él.
Por defecto, el contenedor es capaz de leer (read), escribir (write) y crear nodos (mknod) en estos dispositivos.
Esto se puede invalidar utilizando un tercer conjunto de opciones :rwm para cada flag
--device. Si el contenedor se ejecuta en modo privilegiado, Docker ignora los
permisos especificados.
$ docker run --device=/dev/sda:/dev/xvdc --rm -it ubuntu fdisk /dev/xvdc
Command (m for help): q
$ docker run --device=/dev/sda:/dev/xvdc:r --rm -it ubuntu fdisk /dev/xvdc
You will not be able to write the partition table.
Command (m for help): q
$ docker run --device=/dev/sda:/dev/xvdc:rw --rm -it ubuntu fdisk /dev/xvdc
Command (m for help): q
$ docker run --device=/dev/sda:/dev/xvdc:m --rm -it ubuntu fdisk /dev/xvdc
fdisk: unable to open /dev/xvdc: Operation not permitted
NoteLa opción
--deviceno se puede utilizar de forma segura con dispositivos efímeros. No deberías añadir dispositivos de bloque que puedan ser eliminados a contenedores no confiables con--device.
Para Windows, el formato de la cadena pasada a la opción --device es de la forma
--device=<IdType>/<Id>. A partir de Windows Server 2019
y Windows 10 October 2018 Update, Windows solo admite un IdType de
class y el Id como un GUID de clase de interfaz de dispositivo.
Consulta la tabla definida en los documentos de contenedores de Windows
para obtener una lista de los GUID de clase de interfaz de dispositivo compatibles con contenedores.
Si especificas esta opción para un contenedor de Windows aislado por procesos, Docker hace que todos los dispositivos que implementan el GUID de clase de interfaz de dispositivo solicitado estén disponibles en el contenedor. Por ejemplo, el comando de abajo hace que todos los puertos COM del host sean visibles en el contenedor.
PS C:\> docker run --device=class/86E0D1E0-8089-11D0-9CE4-08003E301F73 mcr.microsoft.com/windows/servercore:ltsc2019NoteLa opción
--devicesolo es compatible con contenedores Windows aislados por procesos, y produce un error si el aislamiento del contenedor eshyperv.
Dispositivos CDI
La Interfaz de Dispositivos de Contenedor (CDI) es un mecanismo estandarizado para que los entornos de ejecución de contenedores creen contenedores que puedan interactuar con dispositivos de terceros.
CDI actualmente solo es compatible con contenedores Linux y está habilitado de forma predeterminada desde Docker Engine 28.3.0.
Con CDI, las configuraciones de los dispositivos se definen de forma declarativa mediante un archivo JSON o YAML. Además de permitir que el contenedor interactúe con el nodo del dispositivo, también te permite especificar configuraciones adicionales para el dispositivo, como variables de entorno, montajes del host (como objetos compartidos) y ganchos (hooks) ejecutables.
Puedes hacer referencia a un dispositivo CDI con el flag --device utilizando el
nombre completo del dispositivo, como se muestra en el siguiente ejemplo:
$ docker run --device=vendor.com/class=device-name --rm -it ubuntu
Esto inicia un contenedor ubuntu con acceso al dispositivo CDI especificado,
vendor.com/class=device-name, asumiendo que:
- Se encuentra disponible en el sistema que ejecuta el demonio una especificación CDI válida (archivo JSON o YAML) para el dispositivo solicitado, en uno de los directorios de especificaciones CDI configurados.
- Se ha habilitado la característica CDI en el demonio; consulta Habilitar dispositivos CDI.
Asociar a STDIN/STDOUT/STDERR (-a, --attach)
El flag --attach (o -a) indica a docker run que se vincule a las entradas y salidas
STDIN, STDOUT o STDERR del contenedor. Esto hace posible manipular la salida
y la entrada según sea necesario. Puedes especificar a cuál de los tres flujos estándar
(STDIN, STDOUT, STDERR) deseas conectarte en su lugar, como en:
$ docker run -a stdin -a stdout -i -t ubuntu /bin/bash
El siguiente ejemplo canaliza datos a un contenedor e imprime el ID del contenedor
asociándose únicamente a la entrada STDIN del contenedor.
$ echo "test" | docker run -i -a stdin ubuntu cat -
El siguiente ejemplo no imprime nada en la consola a menos que haya un
error, porque la salida solo está asociada a STDERR del contenedor. Los
registros (logs) del contenedor siguen almacenando lo que se escribe en STDERR y STDOUT.
$ docker run -a stderr ubuntu echo test
El siguiente ejemplo muestra una forma de utilizar --attach para canalizar un archivo a un
contenedor. El comando imprime el ID del contenedor una vez finalizada la construcción y
puedes recuperar los registros de la construcción utilizando docker logs. Esto es útil si necesitas
canalizar un archivo u otra cosa a un contenedor y recuperar el ID del contenedor
una vez que este ha terminado de ejecutarse.
$ cat somefile | docker run -i -a stdin mybuilder dobuild
NoteUn proceso que se ejecuta como PID 1 dentro de un contenedor recibe un trato especial por parte de Linux: ignora cualquier señal con la acción predeterminada. Por lo tanto, el proceso no finaliza con
SIGINToSIGTERMa menos que esté programado para hacerlo.
Consulta también
el comando docker cp.
Mantener STDIN abierto (-i, --interactive)
El flag --interactive (o -i) mantiene abierta la entrada STDIN del contenedor y te permite
enviar entradas al contenedor a través de la entrada estándar.
$ echo hello | docker run --rm -i busybox cat
hello
El flag -i se utiliza muy a menudo junto con el flag --tty para vincular los flujos de
E/S del contenedor a una pseudoterminal, creando una sesión de terminal interactiva
para el contenedor. Consulta Asignar un pseudo-TTY para más ejemplos.
$ docker run -it debian
root@10a3e71492b0:/# factor 90
90: 2 3 3 5
root@10a3e71492b0:/# exit
exit
Usar el flag -i por sí solo permite la composición, como canalizar entradas a
los contenedores:
$ docker run --rm -i busybox echo "foo bar baz" \
| docker run --rm -i busybox awk '{ print $2 }' \
| docker run --rm -i busybox rev
rab
Especificar un proceso de inicio (init)
Puedes utilizar el flag --init para indicar que se debe utilizar un proceso de inicio como
el PID 1 en el contenedor. Especificar un proceso de inicio garantiza que las responsabilidades
habituales de un sistema de inicio, como la recolección de procesos zombi, se
realicen dentro del contenedor creado.
El proceso de inicio predeterminado utilizado es el primer ejecutable docker-init que se encuentre en la
ruta del sistema del proceso del demonio de Docker. Este binario docker-init, incluido en
la instalación predeterminada, está respaldado por tini.
Asignar un pseudo-TTY (-t, --tty)
El flag --tty (o -t) asocia un pseudo-TTY al contenedor, conectando
tu terminal a los flujos de E/S del contenedor. Asignar un pseudo-TTY al
contenedor significa que obtienes acceso a las funciones de entrada y salida que
proporcionan los dispositivos TTY.
Por ejemplo, el siguiente comando ejecuta el comando passwd en un contenedor debian
para establecer una nueva contraseña para el usuario root.
$ docker run -i debian passwd root
New password: karjalanpiirakka9
Retype new password: karjalanpiirakka9
passwd: password updated successfully
Si ejecutas este comando solo con el flag -i (que te permite enviar texto a
STDIN del contenedor), el prompt de passwd muestra la contraseña en texto plano.
Sin embargo, si intentas lo mismo pero añadiendo también el flag -t, la
contraseña se oculta:
$ docker run -it debian passwd root
New password:
Retype new password:
passwd: password updated successfully
Esto se debe a que passwd puede suprimir la salida de caracteres en la terminal
utilizando la función de desactivación de eco de TTY.
Puedes utilizar el flag -t sin el flag -i. Esto sigue asignando un pseudo-TTY
al contenedor, pero sin forma de escribir en STDIN. El único momento en que esto
puede ser útil es si la salida del contenedor requiere un entorno TTY.
Especificar cgroups personalizados
Utilizando el flag --cgroup-parent, puedes pasar un cgroup específico en el que ejecutar
un contenedor. Esto te permite crear y administrar cgroups por tu cuenta. Puedes
definir recursos personalizados para esos cgroups y colocar contenedores bajo un grupo
principal común.
Utilizar dispositivos creados dinámicamente (--device-cgroup-rule)
Docker asigna los dispositivos disponibles a un contenedor en el momento de la creación. Los dispositivos asignados se añaden al archivo cgroup.allow y se crean en el contenedor cuando se ejecuta. Esto plantea un problema cuando necesitas añadir un nuevo dispositivo a un contenedor en ejecución.
Una solución es añadir una regla más permisiva a un contenedor
permitiéndole el acceso a una gama más amplia de dispositivos. Por ejemplo, suponiendo que
el contenedor necesita acceso a un dispositivo de caracteres con un número mayor (major) 42 y
cualquier número menor (minor) (que se añade a medida que aparecen nuevos dispositivos), añade la
siguiente regla:
$ docker run -d --device-cgroup-rule='c 42:* rmw' --name my-container my-image
Luego, un usuario podría pedir a udev que ejecute un script que ejecute docker exec my-container mknod newDevX c 42 <minor>
en el dispositivo requerido cuando este se añada.
NoteAún debes añadir explícitamente los dispositivos inicialmente presentes al comando
docker run/docker create.
Acceder a una GPU NVIDIA
El flag --gpus te permite acceder a los recursos de la GPU NVIDIA. En primer lugar, debes
instalar nvidia-container-runtime.
NoteTambién puedes especificar una GPU como un dispositivo CDI con el flag
--device, consulta Dispositivos CDI.
Lee Especificar los recursos de un contenedor para más información.
Para utilizar --gpus, especifica qué GPUs (o todas) usar. Si no proporcionas ningún valor, Docker utiliza todas
las GPUs disponibles. El siguiente ejemplo expone todas las GPUs disponibles.
$ docker run -it --rm --gpus all ubuntu nvidia-smi
Utiliza la opción device para especificar las GPUs. El ejemplo de abajo expone una
GPU específica.
$ docker run -it --rm --gpus device=GPU-3a23c669-1f69-c64e-cf85-44e9b07e7a2a ubuntu nvidia-smi
El ejemplo de abajo expone la primera y la tercera GPU.
$ docker run -it --rm --gpus '"device=0,2"' ubuntu nvidia-smi
Políticas de reinicio (--restart)
Utiliza el flag --restart para especificar la política de reinicio de un contenedor. Una política de
reinicio controla si el demonio de Docker reinicia un contenedor después de su salida.
Docker admite las siguientes políticas de reinicio:
| Flag | Descripción |
|---|---|
no | No reinicia automáticamente el contenedor. (Por defecto) |
on-failure[:max-retries] | Reinicia el contenedor si este finaliza debido a un error, lo que se manifiesta como un código de salida distinto de cero. Opcionalmente, limita el número de veces que el demonio de Docker intenta reiniciar el contenedor utilizando la opción :max-retries. La política on-failure solo activa un reinicio si el contenedor finaliza con un fallo. No reinicia el contenedor si el demonio se reinicia. |
always | Reinicia siempre el contenedor si se detiene. Si se detiene manualmente, solo se reinicia cuando el demonio de Docker se reinicia o el propio contenedor se reinicia manualmente. |
unless-stopped | Similar a always, excepto que cuando el contenedor se detiene (manualmente o de otro modo), no se reinicia incluso después de que el demonio de Docker se reinicie. |
$ docker run --restart=always redis
Esto ejecuta el contenedor redis con una política de reinicio always.
Si el contenedor finaliza, Docker lo reinicia.
Cuando una política de reinicio está activa en un contenedor, este se muestra como Up o
Restarting en
docker ps. También puede ser útil utilizar
docker events para ver la política de reinicio en efecto.
Se añade un retraso incremental (el doble del retraso anterior, comenzando en 100 milisegundos)
antes de cada reinicio para evitar saturar el servidor. Esto significa que el
demonio espera 100 ms, luego 200 ms, 400, 800, 1600, etc., hasta que se alcance el
límite de on-failure, se alcance el retraso máximo de 1 minuto o cuando ejecutes
docker stop o docker rm -f sobre el contenedor.
Si un contenedor se reinicia correctamente (se inicia y se ejecuta durante al menos 10 segundos), el retraso se restablece a su valor predeterminado de 100 ms.
Especificar un límite para los intentos de reinicio
Puedes especificar el número máximo de veces que Docker intentará reiniciar el contenedor al utilizar la política on-failure. Por defecto, Docker nunca deja de intentar reiniciar el contenedor.
El siguiente ejemplo ejecuta el contenedor redis con una política de reinicio de
on-failure y un número máximo de reinicios de 10.
$ docker run --restart=on-failure:10 redis
Si el contenedor redis finaliza con un estado de salida distinto de cero más de 10 veces
seguidas, Docker deja de intentar reiniciar el contenedor. Proporcionar un límite máximo de
reinicio solo es válido para la política on-failure.
Inspeccionar los reinicios de los contenedores
El número de reinicios (intentados) de un contenedor se puede obtener utilizando el
comando
docker inspect. Por ejemplo, para obtener el número de
reinicios del contenedor "my-container":
$ docker inspect -f "{{ .RestartCount }}" my-container
2
O bien, para obtener la última vez que el contenedor fue (re)iniciado:
$ docker inspect -f "{{ .State.StartedAt }}" my-container
2015-03-04T23:47:07.691840179Z
Combinar --restart (política de reinicio) con el flag --rm (limpieza) produce
un error. Al reiniciar el contenedor, los clientes conectados se desconectan.
Limpieza (--rm)
Por defecto, el sistema de archivos de un contenedor persiste incluso después de que este finalice. Esto facilita enormemente la depuración, ya que puedes inspeccionar el estado final del contenedor y conservar todos tus datos.
Si ejecutas procesos en primer plano a corto plazo, estos sistemas de archivos de los
contenedores pueden empezar a acumularse. Si deseas que Docker limpie automáticamente el
contenedor y elimine el sistema de archivos cuando este finalice, utiliza el flag --rm:
--rm: Elimina automáticamente el contenedor y sus volúmenes anónimos asociados cuando finalizaNoteSi configuras el flag
--rm, Docker también elimina los volúmenes anónimos asociados al contenedor cuando este se elimina. Esto es similar a ejecutardocker rm -v mi-contenedor. Únicamente se eliminan los volúmenes que se especifican sin nombre. Por ejemplo, al ejecutar el siguiente comando, se elimina el volumen/foo, pero no/bar:$ docker run --rm -v /foo -v awesome:/bar busybox topLos volúmenes heredados a través de
--volumes-fromse eliminan con la misma lógica: si el volumen original se especificó con un nombre, no se elimina.
Añadir entradas al archivo hosts del contenedor (--add-host)
Puedes añadir otros hosts al archivo /etc/hosts de un contenedor utilizando uno o
más flags --add-host. Este ejemplo añade una dirección estática para un host llamado
my-hostname:
$ docker run --add-host=my-hostname=8.8.8.8 --rm -it alpine
/ # ping my-hostname
PING my-hostname (8.8.8.8): 56 data bytes
64 bytes from 8.8.8.8: seq=0 ttl=37 time=93.052 ms
64 bytes from 8.8.8.8: seq=1 ttl=37 time=92.467 ms
64 bytes from 8.8.8.8: seq=2 ttl=37 time=92.252 ms
^C
--- my-hostname ping statistics ---
4 packets transmitted, 4 packets received, 0% packet loss
round-trip min/avg/max = 92.209/92.495/93.052 ms
Puedes envolver una dirección IPv6 entre corchetes:
$ docker run --add-host my-hostname=[2001:db8::33] --rm -it alpine
El flag --add-host admite un valor especial host-gateway que se resuelve en la
dirección IP interna del host. Esto es útil cuando deseas que los contenedores se conecten
a los servicios que se ejecutan en la máquina host.
Se acostumbra a utilizar host.docker.internal como el nombre de host que hace referencia a
host-gateway. Docker Desktop resuelve automáticamente este nombre de host, consulta
Explorar guías de redes en Docker Desktop
y
Configurar la IP de la puerta de enlace del host.
El siguiente ejemplo muestra cómo funciona el valor especial host-gateway. El
ejemplo ejecuta un servidor HTTP que sirve un archivo desde el host al contenedor a través del
nombre de host host.docker.internal, que se resuelve en la IP interna del host.
$ echo "hello from host!" > ./hello
$ python3 -m http.server 8000
Serving HTTP on 0.0.0.0 port 8000 (http://0.0.0.0:8000/) ...
$ docker run \
--add-host host.docker.internal=host-gateway \
curlimages/curl -s host.docker.internal:8000/hello
hello from host!
El flag --add-host también acepta un separador :, por ejemplo:
$ docker run --add-host=my-hostname:8.8.8.8 --rm -it alpine
Controladores de registros (Logging drivers) (--log-driver)
El contenedor puede tener un controlador de registros diferente al del demonio de Docker. Utiliza
la opción --log-driver=<DRIVER> con el comando docker run para configurar el
controlador de registros del contenedor.
Para conocer los controladores de registro admitidos y cómo utilizarlos, consulta Configurar controladores de registro.
Para desactivar el registro de un contenedor, establece el flag --log-driver en none:
$ docker run --log-driver=none -d nginx:alpine
5101d3b7fe931c27c2ba0e65fd989654d297393ad65ae238f20b97a020e7295b
$ docker logs 5101d3b
Error response from daemon: configured logging driver does not support reading
Establecer ulimits en el contenedor (--ulimit)
Dado que la configuración de los ajustes de ulimit en un contenedor requiere privilegios adicionales
no disponibles en el contenedor predeterminado, puedes establecerlos utilizando el flag --ulimit.
Especifica --ulimit con un límite flexible (soft) y un límite estricto (hard) en el formato
<tipo>=<límite flexible>[:<límite estricto>]. Por ejemplo:
$ docker run --ulimit nofile=1024:1024 --rm debian sh -c "ulimit -n"
1024
NoteSi no proporcionas un valor de límite estricto, Docker utiliza el valor del límite flexible para ambos valores. Si no proporcionas ningún valor, estos se heredan de los
ulimitspredeterminados establecidos en el demonio.
NoteLa opción
asestá obsoleta. En otras palabras, no se admite el siguiente script:$ docker run -it --ulimit as=1024 fedora /bin/bash
Opciones admitidas para --ulimit:
| Opción | Descripción |
|---|---|
core | Tamaño máximo de los archivos core creados (RLIMIT_CORE) |
cpu | Límite de tiempo de CPU en segundos (RLIMIT_CPU) |
data | Tamaño máximo del segmento de datos (RLIMIT_DATA) |
fsize | Tamaño máximo de archivo (RLIMIT_FSIZE) |
locks | Número máximo de bloqueos de archivos (RLIMIT_LOCKS) |
memlock | Espacio de direcciones máximo bloqueado en memoria (RLIMIT_MEMLOCK) |
msgqueue | Bytes máximos en colas de mensajes POSIX (RLIMIT_MSGQUEUE) |
nice | Ajuste máximo de prioridad nice (RLIMIT_NICE) |
nofile | Número máximo de descriptores de archivos abiertos (RLIMIT_NOFILE) |
nproc | Número máximo de procesos disponibles (RLIMIT_NPROC) |
rss | Tamaño máximo del conjunto residente (RLIMIT_RSS) |
rtprio | Prioridad máxima de programación en tiempo real (RLIMIT_RTPRIO) |
rttime | Tiempo máximo de ejecución en tiempo real (RLIMIT_RTTIME) |
sigpending | Número máximo de señales pendientes (RLIMIT_SIGPENDING) |
stack | Tamaño máximo de la pila (RLIMIT_STACK) |
Docker envía los valores a la llamada al sistema (syscall) correspondiente del sistema operativo y no realiza ninguna conversión de bytes.
Ten esto en cuenta al establecer los valores.
Para el uso de nproc
Ten cuidado al configurar nproc con el flag ulimit ya que Linux utiliza nproc para establecer el
número máximo de procesos disponibles para un usuario, no para un contenedor. Por ejemplo, inicia cuatro
contenedores con el usuario daemon:
$ docker run -d -u daemon --ulimit nproc=3 busybox top
$ docker run -d -u daemon --ulimit nproc=3 busybox top
$ docker run -d -u daemon --ulimit nproc=3 busybox top
$ docker run -d -u daemon --ulimit nproc=3 busybox top
El cuarto contenedor falla y reporta un error "[8] System error: resource temporarily unavailable".
Esto falla porque el invocador configuró nproc=3, lo que provoca que los tres primeros contenedores agoten
la cuota de tres procesos establecida para el usuario daemon.
Detener contenedor con señal (--stop-signal)
El flag --stop-signal envía la señal de llamada al sistema al
contenedor para que finalice. Esta señal puede ser un nombre de señal en el formato SIG<NOMBRE>,
por ejemplo SIGKILL, o un número entero sin signo que coincida con una posición en la
tabla de llamadas al sistema del kernel, por ejemplo 9.
El valor predeterminado está definido por
STOPSIGNAL
en la imagen, o SIGTERM si la imagen no tiene definido ningún STOPSIGNAL.
Opciones de seguridad opcionales (--security-opt)
| Opción | Descripción |
|---|---|
--security-opt="label=user:USER" | Establece la etiqueta de usuario para el contenedor |
--security-opt="label=role:ROLE" | Establece la etiqueta de rol para el contenedor |
--security-opt="label=type:TYPE" | Establece la etiqueta de tipo para el contenedor |
--security-opt="label=level:LEVEL" | Establece la etiqueta de nivel para el contenedor |
--security-opt="label=disable" | Desactiva el confinamiento de etiquetas para el contenedor |
--security-opt="apparmor=PROFILE" | Establece el perfil de AppArmor que se aplicará al contenedor |
--security-opt="no-new-privileges=true" | Evita que los procesos del contenedor obtengan nuevos privilegios |
--security-opt="seccomp=unconfined" | Desactiva el confinamiento de seccomp para el contenedor |
--security-opt="seccomp=builtin" | Utiliza el perfil seccomp predeterminado (integrado) para el contenedor. Esto se puede utilizar para habilitar seccomp para un contenedor que se ejecuta en un demonio con un perfil predeterminado personalizado establecido, o con seccomp desactivado ("unconfined"). |
--security-opt="seccomp=profile.json" | Archivo JSON de llamadas al sistema permitidas en seccomp que se utilizará como filtro seccomp |
--security-opt="systempaths=unconfined" | Desactiva el confinamiento para las rutas del sistema (rutas enmascaradas, rutas de solo lectura) para el contenedor |
El flag --security-opt te permite invalidar el esquema de etiquetado predeterminado para un
contenedor. Especificar el nivel en el siguiente comando te permite compartir
el mismo contenido entre contenedores.
$ docker run --security-opt label=level:s0:c100,c200 -it fedora bash
NoteNo se admite la traducción automática de etiquetas MLS.
Para desactivar por completo el etiquetado de seguridad de un contenedor, puedes utilizar
label=disable:
$ docker run --security-opt label=disable -it ubuntu bash
Si deseas una política de seguridad más estricta sobre los procesos dentro de un contenedor,
puedes especificar una etiqueta de type personalizada. El siguiente ejemplo ejecuta un contenedor
al que solo se le permite escuchar en puertos de Apache:
$ docker run --security-opt label=type:svirt_apache_t -it ubuntu bash
NoteTendrías que escribir una política que defina el tipo
svirt_apache_t.
Para evitar que los procesos de tu contenedor obtengan privilegios adicionales, puedes utilizar el siguiente comando:
$ docker run --security-opt no-new-privileges -it ubuntu bash
Esto significa que los comandos que elevan privilegios como su o sudo ya no funcionan.
También provoca que los filtros de seccomp se apliquen más tarde, después de que se hayan descartado los privilegios,
lo que puede significar que tengas un conjunto de filtros más restrictivo.
Para más detalles, consulta la documentación del kernel.
On Windows, you can use the --security-opt flag to specify the credentialspec option.
The credentialspec must be in the format file://spec.txt or registry://keyname.
Detener contenedor con tiempo de espera (--stop-timeout)
El flag --stop-timeout establece el número de segundos a esperar a que el contenedor
se detenga después de enviar la señal de llamada al sistema predefinida (ver --stop-signal).
Si el contenedor no finaliza una vez transcurrido el tiempo de espera, se le termina abruptamente por la fuerza
con una señal SIGKILL.
Si estableces --stop-timeout en -1, no se aplica ningún tiempo de espera y el demonio
espera indefinidamente a que el contenedor finalice.
El demonio determina el valor predeterminado, que es de 10 segundos para contenedores Linux y de 30 segundos para contenedores Windows.
Especificar la tecnología de aislamiento para el contenedor (--isolation)
Esta opción es útil en situaciones en las que estás ejecutando contenedores Docker en
Windows. La opción --isolation=<value> establece la tecnología de aislamiento de un contenedor.
En Linux, la única opción admitida es default, que utiliza espacios de nombres de Linux.
Estos dos comandos son equivalentes en Linux:
$ docker run -d busybox top
$ docker run -d --isolation default busybox top
En Windows, --isolation puede tomar uno de estos valores:
| Valor | Descripción |
|---|---|
default | Utiliza el valor especificado por la opción --exec-opt del demonio de Docker o el valor predeterminado del sistema (ver más abajo). |
process | Aislamiento del espacio de nombres con kernel compartido. |
hyperv | Aislamiento basado en particiones del hipervisor Hyper-V. |
El aislamiento predeterminado en los sistemas operativos Windows Server es process, y hyperv
en los sistemas operativos Windows cliente, como Windows 10. El aislamiento de procesos tiene un mejor
rendimiento, pero requiere que la imagen y el host utilicen la misma versión del kernel.
En Windows Server, asumiendo la configuración predeterminada, estos comandos son equivalentes
y dan como resultado un aislamiento de tipo process:
PS C:\> docker run -d microsoft/nanoserver powershell echo process
PS C:\> docker run -d --isolation default microsoft/nanoserver powershell echo process
PS C:\> docker run -d --isolation process microsoft/nanoserver powershell echo processSi has configurado la opción --exec-opt isolation=hyperv en el demonio de Docker, o
estás ejecutando contra un demonio basado en Windows cliente, estos comandos son equivalentes y
dan como resultado un aislamiento de tipo hyperv:
PS C:\> docker run -d microsoft/nanoserver powershell echo hyperv
PS C:\> docker run -d --isolation default microsoft/nanoserver powershell echo hyperv
PS C:\> docker run -d --isolation hyperv microsoft/nanoserver powershell echo hypervEspecificar límites estrictos de memoria disponible para contenedores (-m, --memory)
Estos parámetros siempre establecen un límite superior para la memoria disponible para el contenedor. Linux establece esto
en el cgroup y las aplicaciones del contenedor pueden consultarlo en /sys/fs/cgroup/memory/memory.limit_in_bytes.
En Windows, esto afecta a los contenedores de forma diferente según el tipo de aislamiento que utilices.
Con el aislamiento
process, Windows reporta la memoria completa del sistema host, no el límite, a las aplicaciones que se ejecutan dentro del contenedor.PS C:\> docker run -it -m 2GB --isolation=process microsoft/nanoserver powershell Get-ComputerInfo *memory* CsTotalPhysicalMemory : 17064509440 CsPhyicallyInstalledMemory : 16777216 OsTotalVisibleMemorySize : 16664560 OsFreePhysicalMemory : 14646720 OsTotalVirtualMemorySize : 19154928 OsFreeVirtualMemory : 17197440 OsInUseVirtualMemory : 1957488 OsMaxProcessMemorySize : 137438953344Con el aislamiento
hyperv, Windows crea una máquina virtual de utilidad que es lo suficientemente grande como para contener el límite de memoria, más el sistema operativo mínimo necesario para alojar el contenedor. Ese tamaño se reporta como "Memoria física total".PS C:\> docker run -it -m 2GB --isolation=hyperv microsoft/nanoserver powershell Get-ComputerInfo *memory* CsTotalPhysicalMemory : 2683355136 CsPhyicallyInstalledMemory : OsTotalVisibleMemorySize : 2620464 OsFreePhysicalMemory : 2306552 OsTotalVirtualMemorySize : 2620464 OsFreeVirtualMemory : 2356692 OsInUseVirtualMemory : 263772 OsMaxProcessMemorySize : 137438953344
Configurar parámetros del kernel con espacio de nombres (sysctls) en tiempo de ejecución (--sysctl)
La opción --sysctl establece parámetros del kernel con espacio de nombres (sysctls) en el
contenedor. Por ejemplo, para activar el reenvío de IP en el espacio de nombres de red de los
contenedores, ejecuta este comando:
$ docker run --sysctl net.ipv4.ip_forward=1 someimage
NoteNo todos los sysctls tienen espacio de nombres. Docker no admite el cambio de sysctls dentro de un contenedor si estos también modifican el sistema host. A medida que el kernel evolucione, esperamos ver más sysctls con espacio de nombres.
Sysctls admitidos actualmente
Espacio de nombres IPC:
kernel.msgmax,kernel.msgmnb,kernel.msgmni,kernel.sem,kernel.shmall,kernel.shmmax,kernel.shmmni,kernel.shm_rmid_forced.- Sysctls que comienzan con
fs.mqueue.* - Si utilizas la opción
--ipc=host, estos sysctls no están permitidos.
Espacio de nombres de red:
- Sysctls que comienzan con
net.* - Si utilizas la opción
--network=host, el uso de estos sysctls no está permitido.