User Tools

Site Tools


informatica:linux:docker

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
informatica:linux:docker [2019/02/07 12:34] – [Prueba] javiinformatica:linux:docker [2023/03/16 10:18] (current) jose
Line 35: Line 35:
  
   sudo service docker restart   sudo service docker restart
 +
 +===== Habilitar debug =====
 +
 +https://success.docker.com/article/how-do-i-enable-debug-logging-of-the-docker-daemon
 +
 +1. Editar:
 +
 +  sudo vim /etc/docker/daemon.json
 +
 +Y añadir:
 +
 +<code>
 +{
 +    "debug": true
 +}
 +</code>
 +
 +2. Recargar el servicio:
 +
 +  sudo kill -SIGHUP $(pidof dockerd)
 +  
 +3. Ver logs
 +
 +  sudo tail -F /var/log/daemon.log
 +  
 +
 +
  
 ====== Ejecutar como no root ====== ====== Ejecutar como no root ======
Line 121: Line 148:
  
 ====== Cambiar politica de reinicio de contenedor ====== ====== Cambiar politica de reinicio de contenedor ======
 +https://docs.docker.com/config/containers/start-containers-automatically/
  
-Con el contenedor corriendo:+Miramos que política tiene: 
 +  docker inspect container_name| jq -r '.[0].HostConfig.RestartPolicy' 
 +<code> 
 +
 +  "Name": "always", 
 +  "MaximumRetryCount":
 +
 +</code> 
 + 
 +^Flag^Description^ 
 +|no|Do not automatically restart the container. (the default)| 
 +|on-failure|Restart the container if it exits due to an error, which manifests as a non-zero exit code.| 
 +|always|Always restart the container if it stops. If it is manually stopped, it is restarted only when Docker daemon restarts or the container itself is manually restarted. (See the second bullet listed in restart policy details)| 
 +|unless-stopped|Similar to always, except that when the container is stopped (manually or otherwise), it is not restarted even after Docker daemon restarts.| 
 + 
 + 
 +Para cambiarlo
  
   docker update --restart unless-stopped container_name   docker update --restart unless-stopped container_name
Line 132: Line 176:
   * Network. Caracteristica soportada por la version 1.9. Dejara obsoleta la opcion "--link"    * Network. Caracteristica soportada por la version 1.9. Dejara obsoleta la opcion "--link" 
   * IPs estaticas para contenedores. Esta previsto introducirla en la version 1.10, prevista para febrero de 2016   * IPs estaticas para contenedores. Esta previsto introducirla en la version 1.10, prevista para febrero de 2016
 +
 +Hay un excelente artículo que las explica:
 +
 +https://docs.docker.com/network/network-tutorial-standalone/#use-the-default-bridge-network
 +
 +===== Visibilidad contenedor_a <-> contenedor_b =====
 +
 +La opción "--link" debe evitarse, está en desuso.
 +
 +Hay que resolver dos cuestiones:
 +
 +1. Que haya conectividad a nivel de red entre contenedores
 +2. Que cada contenedor pueda acceder por nombre al otro contenedor.
 +
 +**IMPORTANTE**: la gracia es que si se destruye un contenedor y se vuelve a crear, se pueda detener y arrancar el otro contenedor. Con "--link" si se destruye el contenedor "enlazado", al detener el contenedor que lo referenciaba e intentar arrancarlo de nuevo NO podremos.
 +
 +==== Sin docker compose ====
 +
 +En este ejemplo:
 +
 +  * Tenemos 3 contenedores 3, "sever_a", "server_b" y "server_c"
 +  * server_a y server_b tienen conectividad
 +  * Desde server_a se puede llegar a server_b por nombre
 +  * Desde server_b se puede llegar a server_a por nombre
 +  * Si se destruye server_b, se vuelve a crear y se detiene server_a, se podrá volver a arrancar server_a
 +  * server_c no llega a nivel de red (ni resuelve el nombre) de server_a ni de server_b
 +
 +1. Crear la red
 +
 +<code>
 +docker network create network-private
 +</code>
 +
 +2. Creamos los 3 contenedores 3
 +
 +<code>
 +docker run --name server_a \
 + -ti \
 + --network network-private \
 + --net-alias server_a \
 + -d debian
 +</code>
 +
 +<code>
 +docker run --name server_b \
 + -ti \
 + --network network-private \
 + --net-alias server_b \
 + -d debian
 +</code>
 +
 +<code>
 +docker run --name server_c \
 + -ti \
 + -d debian
 +</code>
 +
 +3. Desde "server_a" llegamos a "server_b" por nombre:
 +
 +3.1. Nos conectamos
 +
 +<code>
 +docker exec -ti server_a bash
 +</code>
 +
 +3.2. Ejecutamos:
 +
 +<code>
 +ping server_b
 +</code>
 +
 +Resultado esperado similar a:
 +
 +<code>
 +PING server_b (192.168.224.3) 56(84) bytes of data.
 +64 bytes from server_b.network-private (192.168.224.3): icmp_seq=1 ttl=64 time=0.222 ms
 +64 bytes from server_b.network-private (192.168.224.3): icmp_seq=2 ttl=64 time=0.134 ms
 +^C
 +--- server_b ping statistics ---
 +2 packets transmitted, 2 received, 0% packet loss, time 1013ms
 +rtt min/avg/max/mdev = 0.134/0.178/0.222/0.044 ms
 +root@34e909656151:/# 
 +</code>
 +
 +3.3. Salimos
 +
 +<code>
 +exit
 +</code>
 +
 +4. Re-creamos "server_b"
 +
 +<code>
 +docker stop server_b && docker rm server_b
 +</code>
 +
 +<code>
 +docker run --name server_b \
 + -ti \
 + --network network-private \
 + --net-alias server_b \
 + -d debian
 +</code>
 +
 +5. Detenemos y arrancamos "server_a"
 +
 +<code>
 +docker stop server_a
 +</code>
 +
 +Al arrancarlo:
 +
 +<code>
 +docker stop server_a
 +</code>
 +
 +NO nos da ningún error. Si hubiésemos usado la opción "--link" no hubiéramos podido arrancarlo
 +
 +6. Repetir el paso 3. Debemos obtener el mismo resultado
 +
 +7. Limpiamos
 +
 +<code>
 +docker stop server_a && docker rm server_a
 +docker stop server_b && docker rm server_b
 +docker stop server_c && docker rm server_c
 +docker network rm network-private 
 +</code>
 +
 +==== Con docker compose ====
 +
 +1. Crear el siguiente archivo:
 +
 +<code>
 +version: '3.7'
 +services:
 +
 + server_a:
 +  container_name: server_a
 +  image: debian
 +  stdin_open: true
 +  tty: true
 +  networks:
 +   network-private:
 +    aliases:
 +    - server_a
 +
 + server_b:
 +  container_name: server_b
 +  image: debian
 +  stdin_open: true
 +  tty: true
 +  networks:
 +   network-private:
 +    aliases:
 +    - server_b
 +
 + server_c:
 +  container_name: server_c
 +  image: debian
 +  stdin_open: true
 +  tty: true
 +  
 +networks:
 +  network-private:
 +    name: network-private
 +</code>
 +
 +2. Levantar el entorno:
 +
 +<code>
 +docker-compose up -d
 +</code>
 +
 +3. Realizar las mismas pruebas que en el apartado anterior (re-crear el contenedor se tendrá que hacer a mano, sin docker-compose)
 +
 +4. Para limpiar:
 +
 +4.1. Eliminar a mano "server_b"
 +
 +<code>
 +docker stop server_b && docker rm server_b
 +</code>
 +
 +4.2. Pararlo todo
 +
 +<code>
 +docker-compose down
 +</code>
 +
  
 ====== Puertos ====== ====== Puertos ======
Line 192: Line 426:
  
   docker inspect --format '{{ .NetworkSettings.IPAddress }}' container_id   docker inspect --format '{{ .NetworkSettings.IPAddress }}' container_id
 +
 +  * Obtener puertos que tiene abiertos internamente (con jq):
 +
 +  docker inspect container_id |jq .[].NetworkSettings.Ports
  
   * Renombrar container:   * Renombrar container:
Line 850: Line 1088:
 Para mostrar estadísticas de consumo de recursos por contenedor: Para mostrar estadísticas de consumo de recursos por contenedor:
  
-  docker stats --format "table {{.Name}}\t{{.CPUPerc}}\t{{.MemPerc}}\t{{.MemUsage}}"+  watch -n 5 'docker stats --no-stream --format "table {{.Name}}\t{{.Container}}\t{{.CPUPerc}}\t{{.MemUsage}}" | sort -r -k 3 -h' 
 + 
 +====== Usar variables de entorno en tiempo de arranque ====== 
 + 
 +1. Crear script de arranque 
 + 
 +<code> 
 +mkdir /tmp/aux 
 +cd /tmp/aux 
 +vim entrypoint.sh 
 +</code> 
 + 
 +Con el siguiente contenido: 
 + 
 +<code> 
 +#!/bin/bash 
 +echo "Content of VAR1 is: _"$VAR1"_" 
 +</code> 
 + 
 +2. Crear Dockerfile: 
 + 
 +<code> 
 +cd /tmp/aux 
 +vim Dockerfile 
 +</code> 
 + 
 +Con el siguiente contenido: 
 + 
 +<code> 
 +FROM debian:testing 
 + 
 +COPY entrypoint.sh / 
 + 
 +RUN chmod +x /entrypoint.sh 
 + 
 +ENTRYPOINT ["/entrypoint.sh"
 +</code> 
 + 
 +3. Probar 
 + 
 +<code> 
 +docker build . -t localhost/test && docker stop test && docker rm test && docker run --name test -ti -e VAR1=patata localhost/test 
 +</code> 
 + 
 +La última linea de la salida debería ser: 
 + 
 +<code> 
 +Content of VAR1 is: _patata_ 
 +</code> 
 + 
 +4. Limpiar 
 + 
 +<code> 
 +docker stop test && docker rm test && docker rmi localhost/test 
 +</code> 
 + 
 +====== Timezone ====== 
 + 
 +Para ganar tiempo dejo algunos ejemplos de cómo configurar el timezone dependiendo de la imagen 
 + 
 +===== Alpine ===== 
 + 
 +Hay que hacer 2 cosas: 
 + 
 +1. Instalar el paquete "tzdata" 
 + 
 +<code> 
 +apk add tzdata 
 +</code> 
 + 
 +2. Configurar la variable de entorno "TZ" 
 + 
 +===== Debian (p.ej.python:3-stretch) ===== 
 + 
 +Hay que hacer 1 cosa: 
 + 
 +1. Crear un enlace simbólico. En este ejemplo usamos la variable "$TZ", pero se puede "hardcodear" a "Europe/Madrid" por ejemplo 
 + 
 +<code> 
 +ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone 
 +</code> 
  
 ====== Errores ====== ====== Errores ======
Line 932: Line 1251:
   docker ps | grep dns   docker ps | grep dns
  
 +===== ERROR: Service 'logrotate' failed to build: invalid reference format =====
 +
 +Escenario:
 +
 +* Uso docker compose
 +* Uso build dentro del docker compose
 +* La imagen y la versión se pasan por parámetro
 +
 +**docker-compose.yml**
 +
 +<code>
 +version: '3.7'
 +services:
 +
 + logrotate:
 +  build:
 +   context: ./path/to/dir
 +   args:
 +    - IMAGE=${IMAGE}
 +    - VERSION=${VERSION}
 +...
 +</code>
 +
 +**Dockerfile** (dentro de './path/to/dir')
 +
 +<code>
 +ARG IMAGE
 +
 +ARG VERSION
 +
 +FROM $IMAGE:$VERSION
 +...
 +</code>
 + 
 +**.env**
 +
 +<code>
 +IMAGE=
 +VERSION=latest
 +</code>
 +
 +Solución:
 +
 +Revisar que las variables "IMAGE" y "VERSION" sean coherentes. En este caso por error IMAGE estaba vacía
 +
 +===== ERROR: yaml.parser.ParserError: while parsing a block mapping =====
 +
 +Error completo:
 +
 +<code>
 +ERROR: yaml.parser.ParserError: while parsing a block mapping
 +  in "./docker-compose.analytics-celery-v3.yml", line 1, column 1
 +expected <block end>, but found '<block mapping start>'
 +  in "./docker-compose.analytics-celery-v3.yml", line 14, column 2
 +</code>
 +
 +Asegurarse que todos los servicios están alineados a la misma altura.
 +
 +**KO**
 +
 +<code>
 +version: '3.7'
 +services:
 +
 +  logrotate-legacy:
 +    build:
 +      context: ./services/logrotate/
 +      dockerfile: Dockerfile
 +    container_name: logrotate-legacy
 +    environment:
 +      - LOGROTATE_LOGFILES=/var/log/plc/*.log
 +    volumes:
 +      - /var/log/plc/:/var/log/plc/:rw
 +
 + logrotate:
 +  container_name: ${LOGROTATE_NAME}
 +  image: ${LOGROTATE_IMAGE_LOCAL}/${LOGROTATE_NAME}:${LOGROTATE_VERSION}
 +  restart: ${LOGROTATE_RESTART}
 +  volumes:
 +   - ${LOGROTATE_VOLUME_PLC_HOST}:${LOGROTATE_VOLUME_PLC_CONTAINER}
 +  build:
 +   #context: ./services/logrotate
 +   context: ./services/logrotate-v2/
 +   args:
 +    - IMAGE=${LOGROTATE_IMAGE}
 +    - VERSION=${LOGROTATE_VERSION}
 +    - LOGROTATE_LOGFILES=${LOGROTATE_LOGROTATE_LOGFILES}
 +
 +networks:
 + network-logrotate:
 +  name: ${NETWORK_LOGROTATE}
 +
 +</code>
 +
 +**OK**
 +
 +<code>
 +version: '3.7'
 +services:
 +
 + logrotate-legacy:
 +    build:
 +      context: ./services/logrotate/
 +      dockerfile: Dockerfile
 +    container_name: logrotate-legacy
 +    environment:
 +      - LOGROTATE_LOGFILES=/var/log/plc/*.log
 +    volumes:
 +      - /var/log/plc/:/var/log/plc/:rw
 +
 + logrotate:
 +  container_name: ${LOGROTATE_NAME}
 +  image: ${LOGROTATE_IMAGE_LOCAL}/${LOGROTATE_NAME}:${LOGROTATE_VERSION}
 +  restart: ${LOGROTATE_RESTART}
 +  volumes:
 +   - ${LOGROTATE_VOLUME_PLC_HOST}:${LOGROTATE_VOLUME_PLC_CONTAINER}
 +  build:
 +   #context: ./services/logrotate
 +   context: ./services/logrotate-v2/
 +   args:
 +    - IMAGE=${LOGROTATE_IMAGE}
 +    - VERSION=${LOGROTATE_VERSION}
 +    - LOGROTATE_LOGFILES=${LOGROTATE_LOGROTATE_LOGFILES}
 +
 +networks:
 + network-logrotate:
 +  name: ${NETWORK_LOGROTATE}
 +
 +</code>
 +
 +===== does not match any of the regexes: '^x-' =====
 +
 +Error completo:
 +
 +<code>
 +ERROR: The Compose file './docker-compose.rafa.yml' is invalid because:
 +networks.network-rafa-db value 'network-proxy' does not match any of the regexes: '^x-'
 +</code>
 +
 +**Causa**
 +
 +Un bloque, en este caso dentro de networks, no está alineado correctamente
 +
 +**Solución**
 +
 +1. Identificar el bloque, en este caso "networks"
 +
 +2. Revisar las entradas. Una de ellas tiene un espacio de más o de menos
 +
 +===== Servidor tarda en apagarse esperando por contenedores docker =====
 +
 +https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=989490#14
 +
 +===== Docker build con variables =====
 +Si queremos tener versionado un docker, por ejemplo con versiones diferentes de node.js desde el build.\\
 +Instala por defecto la version 16.13.0
 +
 +<code>
 +FROM debian
 +
 +ARG NODE_VERSION=16.13.0
 +
 +RUN wget https://nodejs.org/download/release/v$NODE_VERSION/node-v$NODE_VERSION-linux-x64.tar.xz
 +RUN mkdir -p /usr/local/lib/nodejs
 +
 +RUN tar -xJvf node-v$NODE_VERSION-linux-x64.tar.xz -C /usr/local/lib/nodejs 
 +
 +CMD ["bash", "-l"]
 +</code>
  
  
 +Si quisiera crear una imagen con otra versión:
 +  docker build --build-arg NODE_VERSION=18.15.0 -f Dockerfile -t node:18.15 .
informatica/linux/docker.1549542856.txt.gz · Last modified: 2019/02/07 12:34 by javi