web-dev-qa-db-fra.com

Comment puis-je faire en sorte que mon script Docker compose "attendre qu'il" appelle le conteneur d'origine ENTRYPOINT ou CMD?

Selon Contrôle de l'ordre de démarrage dans Compose , on peut contrôler l'ordre dans lequel Docker Compose démarre les conteneurs en utilisant un " wait-for-it " scénario. Script wait-for-it.sh attend à la fois un Host:port argument ainsi que la commande que le script doit exécuter lorsque le port est disponible. La documentation recommande que Docker Compose appelle ce script à l'aide de entrypoint: option. Cependant, si l'on utilise cette option, le conteneur n'exécutera plus sa valeur par défaut ENTRYPOINT ou CMD car entrypoint: remplace la valeur par défaut.

Comment peut-on fournir cette commande par défaut à wait-for-it.sh pour que le script puisse invoquer la valeur par défaut ENTRYPOINT ou CMD lorsque la condition attendue est remplie?

Dans mon cas, j'ai implémenté un script wait-for-file.sh qui interroge en attendant qu'un fichier existe:

#!/bin/bash

set -e

waitFile="$1"
shift
cmd="$@"

until test -e $waitFile
do
  >&2 echo "Waiting for file [$waitFile]."
  sleep 1
done

>&2 echo "Found file [$waitFile]."
exec $cmd

Docker Compose invoque wait-for-file.sh comme point d'entrée vers un conteneur légèrement personnalisé dérivé de Tomcat:8-jre8 :

  platinum-oms:
    image: opes/platinum-oms
    ports:
      - "8080:8080"
    volumes_from:
      - liquibase
    links:
      - postgres:postgres
      - activemq:activemq
    depends_on:
      - liquibase
      - activemq
    entrypoint: /wait-for-file.sh /var/run/liquibase/done

Avant de se terminer avec succès, un autre conteneur personnalisé liquibase crée /var/run/liquibase/done et donc platinum-oms attend effectivement que le conteneur liquibase se termine.

Une fois que le conteneur liquibase crée le fichier /var/run/liquibase/done, wait-for-file.sh imprime Found file [/var/run/liquibase/done]., mais ne parvient pas à appeler la commande par défaut catalina.sh run dans le conteneur de base Tomcat:8-jre8. Pourquoi?

Scénario de test

J'ai créé un scénario de test simplifié docker-compose-wait-for-file pour démontrer mon problème. Récipient ubuntu-wait-for-file attend le conteneur ubuntu-create-file pour créer le fichier /wait/done puis j'attends le conteneur ubuntu-wait-for-file pour appeler la commande par défaut ubuntu container /bin/bash, mais à la place, il se ferme. Pourquoi ça ne marche pas comme je m'y attend?

20
Derek Mahar

Cependant, si l'on utilise cette option, le conteneur n'exécutera plus sa commande par défaut ENTRYPOINT ou CMD car entrypoint: remplace la valeur par défaut.

C'est prévu, c'est pourquoi le wait-for-it est présenté comme un script wrapper .
Il permet cependant d'exécuter une "sous-commande":

wait-for-it.sh Host:port [-s] [-t timeout] [-- command args]
                                               ^^^^^^^^^^^^

La sous-commande sera exécutée, que le service soit actif ou non.
Si vous souhaitez exécuter la sous-commande uniquement si le service est actif, ajoutez le --strict argument.

Cela signifie que la partie CMD de votre image peut être utilisée pour votre commande de conteneur réelle, car ses paramètres seront passés en paramètres à la commande ENTRYPOINT:

entrypoint: wait-for-it.sh Host:port --
cmd: mycmd myargs

Cela devrait fonctionner ... sauf pour docker-compose problème 314 (mentionné par le OP Derek Mahar dans les commentaires )

point d'entrée défini dans docker-compose.yml efface CMD défini dans Dockerfile

8
VonC