Domina `docker inspect`: Cómo extraer metadatos de contenedores e imágenes

DUGLAS MORENODUGLAS MORENO 👁 16

Introducción

Cuando trabajás con Docker, saber qué tiene una imagen o un contenedor es vital. Ya sea que quieras depurar un comportamiento inesperado, optimizar la puesta en producción o simplemente entender la configuración que se le está pasando a un contenedor, el comando docker inspect es tu herramienta de referencia. Este post va a:

  1. Explicar de qué va a tratar cada campo más relevante del JSON que devuelve.
  2. Mostrarse ejemplos de uso, con la salida esperada para que tengas una referencia.
  3. Darte buenas prácticas y errores comunes al manejar estas respuestas.

Está dirigido a desarrolladores, DevOps y a cualquiera que esté empezando con Docker y necesite leer los metadata de sus recursos.

¿Qué es docker inspect?

docker inspect es un comando de Docker que devuelve información estructurada en JSON sobre objetos de Docker: contenedores, imágenes, volúmenes, redes, etc. A diferencia de docker ps o docker images, que ofrecen una vista tabular y resumida, inspect te entrega el gordo del objeto, con todas sus propiedades internas.

docker inspect <objeto>

El <objeto> puede ser un ID, un nombre o cualquier referencia válida. Por ejemplo, docker inspect my_container o docker inspect ubuntu:latest.

A continuación, profundizaremos en los campos más útiles.

1. Metadatos de un contenedor

Cuando inspeccionás un contenedor, Docker devuelve un array con un solo elemento que contiene toda la información. La estructura más relevante es la siguiente:

Campo Descripción Tipo Ejemplo Comentario
Id SHA-1 del contenedor string a1b2c3d4... Útil para referenciarlo internamente.
Image SHA-1 de la imagen base string sha256:7890... Toma nota que no es el tag.
Command El comando ejecutado al iniciar array ['/bin/sh', '-c', 'python app.py'] Representa el CMD o ENTRYPOINT.
Created Timestamp string 2024-07-01T12:34:56.789Z En UTC.
State Estado actual object { "Running": true, "Paused": false, ... } Incluye ExitCode, Error, StartedAt.
NetworkSettings Info de redes, IPs, puertos object { "Networks": { "bridge": { "IPAddress": "172.17.0.2" } } } Crucial para depurar puertos expuestos.
Mounts Volúmenes montados array [{ "Source": "/tmp/data", "Destination": "/app/data", "Mode": "rw", "RW": true, "Propagation": "private" }] Sirve para ver bind-mounts y volúmenes.
Config Configuración de ejecución object { "Hostname": "my_container", "Env": ["VAR=value"], "Cmd": ["python", "app.py"] } Mostrará variables de entorno y comando.
HostConfig Configuración de host object { "Binds": ["/tmp/data:/app/data"], "PortBindings": { "80/tcp": [{ "HostPort": "8080" }] } } Información de puertos y mounts a nivel de host.

1.1 Ejemplo práctico

Creemos un contenedor simple y luego lo inspeccionemos.

# Creamos un contenedor con bind-mount y puerto expuesto
run: bash
docker run -d --name demo_container \
  -v $(pwd)/data:/app/data \
  -p 8080:80 \
  nginx:alpine

Ahora inspeccionamos:

run: bash
docker inspect demo_container > demo_container_inspect.json

Salida esperada (fragmento reducido):

[
  {
    "Id": "f6d2c6e9b5e5...",
    "Image": "sha256:9c2d...",
    "Command": ["/usr/sbin/nginx", "-g", "daemon off;"] ,
    "Created": "2024-07-02T14:12:45.123Z",
    "State": {
      "Running": true,
      "Paused": false,
      "Restarting": false,
      "OOMKilled": false,
      "Dead": false,
      "Pid": 1234,
      "ExitCode": 0,
      "Error": "",
      "StartedAt": "2024-07-02T14:12:46.789Z",
      "FinishedAt": "0001-01-01T00:00:00Z"
    },
    "NetworkSettings": {
      "Networks": {
        "bridge": {
          "IPAddress": "172.17.0.3"
        }
      }
    },
    "Mounts": [
      {
        "Source": "/home/user/data",
        "Destination": "/app/data",
        "Mode": "rw",
        "RW": true,
        "Propagation": "private"
      }
    ],
    "Config": {
      "Hostname": "demo_container",
      "Env": [],
      "Cmd": ["/usr/sbin/nginx", "-g", "daemon off;"],
      "Image": "nginx:alpine"
    },
    "HostConfig": {
      "Binds": ["/home/user/data:/app/data:rw"],
      "PortBindings": {
        "80/tcp": [
          {
            "HostPort": "8080"
          }
        ]
      }
    }
  }
]

Interpretación clave:

  • Mounts y HostConfig.Binds coinciden; el primero es la vista a nivel de contenedor, el segundo a nivel de host.
  • NetworkSettings.Networks.bridge.IPAddress te muestra la IP interna asignada.
  • HostConfig.PortBindings refleja la relación entre puertos internos y externos.

2. Metadatos de una imagen

La inspección de imágenes devuelve una lista de objetos, cada uno con información sobre la capa, sus comandos, variables de entorno y más.

Campo Descripción Tipo Ejemplo
Id SHA-1 de la imagen string sha256:...
RepoTags Los tags asociados array ["myapp:1.0", "myapp:latest"]
Created Timestamp de construcción string
Size Tamaño en bytes integer
VirtualSize Tamaño total de capas integer
Config Configuración del contenedor que se crea a partir de esta imagen object { "Env": ["DEBUG=1"], "Cmd": ["python", "app.py"] }
RootFS Información de capas object { "Layers": ["sha256:abc...", "sha256:def..."], "Type": "layers" }
Architecture Arquitectura string amd64
Os Sistema operativo string linux
Labels Etiquetas de metadata object { "maintainer": "alice@example.com" }

2.1 Ejemplo práctico

run: bash
docker pull busybox:1.36

Inspeccionamos la imagen:

run: bash
docker inspect busybox:1.36 > busybox_inspect.json

Salida esperada (fragmento reducido):

[
  {
    "Id": "sha256:1a2b3c...",
    "RepoTags": ["busybox:1.36"],
    "RepoDigests": [],
    "Parent": "",
    "Comment": "",
    "Created": "2024-06-30T10:22:11.123Z",
    "Container": "",
    "ContainerConfig": {
      "Hostname": "",
      "Domainname": "",
      "User": "",
      "AttachStdin": false,
      "AttachStdout": false,
      "AttachStderr": false,
      "Tty": false,
      "OpenStdin": false,
      "StdinOnce": false,
      "Env": [],
      "Cmd": ["/bin/sh"],
      "Image": "",
      "Volumes": {},
      "WorkingDir": "",
      "Entrypoint": [],
      "OnBuild": [],
      "Labels": {}
    },
    "DockerVersion": "26.1.0",
    "Author": "",
    "Config": {
      "Hostname": "",
      "Domainname": "",
      "User": "",
      "AttachStdin": false,
      "AttachStdout": false,
      "AttachStderr": false,
      "Tty": false,
      "OpenStdin": false,
      "StdinOnce": false,
      "Env": [],
      "Cmd": ["/bin/sh"],
      "ArgsEscaped": true,
      "Image": "",
      "Volumes": {},
      "WorkingDir": "",
      "Entrypoint": [],
      "OnBuild": [],
      "Labels": {}
    },
    "Architecture": "amd64",
    "Os": "linux",
    "Size": 1457726,
    "VirtualSize": 1457726,
    "GraphDriver": {
      "Data": {},
      "Name": "overlay2"
    },
    "RootFS": {
      "Type": "layers",
      "Layers": [
        "sha256:abcd..."
      ]
    }
  }
]

Interpretación clave:

  • Size te da el tamaño de la capa ya reducida a su estado final.
  • VirtualSize indica el tamaño acumulado de todas las capas que componen la imagen.
  • La sección Config reproduce el Dockerfile de la última capa: comandos, variables y entrada.

3. Filtrar la salida JSON

En la práctica, la salida completa suele ser demasiado verbosa. Docker permite filtrar con --format o con jq locales.

3.1 Usar la plantilla --format

run: bash
# Obtener solo el IP interno del contenedor
Docker inspect demo_container --format '{{.NetworkSettings.Networks.bridge.IPAddress}}'

3.2 Usar jq (ejemplo)

run: bash
cat demo_container_inspect.json | jq '.[0].Mounts[].Source'

4. Buenas prácticas y errores comunes

Problema Solución Comentarios
Múltiples contenedores con el mismo nombre Usar `docker inspect $(docker ps -q --filter

Comentarios (0)

Sé el primero en comentar.

Dejá tu comentario