Je veux utiliser une sortie de console comme nom de mon image de base du docker.
Plus précisément, j'ai une chaîne de fichiers de construction de docker dépendants, donc j'essaie d'automatiser ce processus. Ainsi, par exemple, le Dockerfile d'une image dérivée1
dépend de l'image de base base_image_name
dans le scénario suivant:
BASE=base_image_name Sending build context to Docker daemon 5.12kB Step 1/3 : FROM company:$BASE invalid reference format
Lorsque l'image de base se construit, elle récupère son nom dans son dossier actuel en utilisant $ {PWD ## * /}
. Dans ce cas, le dossier de l'image de base s'appelle base_image_name
, et donc l'image de base s'appelle company: base_image_name
.
Ensuite, lorsque les images dérivées se construisent, elles devraient simplement être capables de comprendre le nom de l'image de base en remontant un répertoire et en regardant le nom de ce répertoire. Ainsi, par exemple, lors de la construction de l'image company: derived1
, elle doit rechercher un répertoire, voir qu'il s'appelle base_image_name
, et à partir de là déduire qu'il doit utiliser le image de base company:base_image_name
.
Je voudrais avoir cette structure plusieurs couches profondes, donc je veux l'automatiser. Pour ce faire, j'ai essayé plusieurs permutations de la syntaxe
FROM company:$BASE
mais je n'arrive pas à faire les choses correctement. Pour comprendre ce que fait la commande $ (cd $ PWD /../; echo $ {PWD ## * /})
, tapez-la simplement dans votre terminal.
build.sh: BASE=$(cd $PWD/../../; echo ${PWD##*/}) echo "BASE="$BASE docker build --build-arg BASE=${BASE} -t company:"${PWD##*/}" .
renvoie simplement le nom du répertoire d'un niveau supérieur. Cependant, lorsque j'essaye d'utiliser ceci dans un Dockerfile, j'obtiens l'erreur
Error response from daemon: Dockerfile parse error line 1: FROM requires either one or three arguments
Quelqu'un pourrait-il me fournir la syntaxe correcte?
EDIT:
J'ai également essayé de construire les images dérivées avec un build-arg
, mais cela ne semble pas non plus fonctionner:
echo $(cd $PWD/../; echo ${PWD##*/})
à quoi ressemble le Dockerfile
FROM company:$(cd $PWD/../; echo ${PWD##*/})
Plus précisément, cela génère l'erreur de construction:
base_image_name/ Dockerfile derived1/ Dockerfile derived2/ Dockerfile
Il semble donc que docker n'interprète pas correctement cet argument de construction.
3 Réponses :
Vous essayez d'utiliser la substitution de commande bash dans quelque chose qui n'est pas consommé par bash.
La [Référence Dockerfile [( https://docs.docker.com/engine/) reference / builder / ) indique que la substitution de variable d'environnement est prise en charge par l'instruction FROM
.
Vous devrez à la place simplement utiliser une variable d'environnement dans FROM
que vous calculez en dehors du Dockerfile et passez à docker build
.
Oh. C'est dommage
Les fichiers Dockerfiles ne prennent pas en charge la syntaxe du shell en général, à l'exception de certains très expansion limitée des variables d'environnement .
Ils prennent en charge les ARG
qui peuvent être transmis à partir de la ligne de commande, et un ARG
peut être utilisé pour définir l'image FROM
. Vous pouvez donc démarrer votre Dockerfile avec
docker build --build-arg tag=$(cd $PWD/../; echo ${PWD##*/}) .
puis créer l'image avec
ARG tag FROM company:${tag:-latest}
(ce qui est suffisamment impliqué pour peut vouloir l'écrire dans un script shell).
À un niveau très bas, il convient également de se rappeler que docker build
fonctionne en créant un fichier tar du répertoire courant, en envoyant via une connexion HTTP au démon Docker et exécutez la compilation là-bas. Une fois ce processus terminé, toute notion du nom du répertoire hôte est perdue. En d'autres termes, même si la syntaxe fonctionnait, docker build
n'a pas non plus la capacité de savoir dans quel répertoire hôte se trouve le Dockerfile.
Oops. J'ai posté ma réponse à quelques secondes de la vôtre
Aha. Je l'ai trouvé.
Comme le souligne Jonathon, il semble que vous ne puissiez pas facilement extraire des éléments de votre environnement dans le système de construction. Il semble que vous deviez utiliser les build-arg
s Docker.
La solution était d'évaluer la variable dans le terminal et de la passer en tant que build-arg
:
ARG BASE FROM company:$BASE
Puis à l'intérieur le Dockerfile de l'image dérivée:
build.sh: BASE=$(cd $PWD/../; echo ${PWD##*/}) echo "BASE="$BASE docker build --build-arg BASE=${BASE} -t company:"${PWD##*/}" .
Votre complexité vient du fait que vous essayez d'utiliser un fichier docker pour la création et le déploiement. Créez vos images séparément à l'aide de scripts simples, puis utilisez votre fichier de composition uniquement pour définir la façon dont vos services sont déployés.
@Alkaline Qui a déjà dit quoi que ce soit à propos de Compose ou de déploiement?