TL;DR
Wenn Sie ARG mit einer mehrstufigen Docker-Datei verwenden, beachten Sie, dass der Bereich innerhalb der Bühne geschlossen ist! Deklarieren Sie das ARG für jede Stufe! Wenn das in mehreren Stufen verwendete ARG einen Standardwert hat, definieren Sie ein globales ARG und geben Sie dort den Standardwert ein!
Es ist okay, wenn du es so machst!
Dockerfile
#Wenn es einen Standardwert für das ARG gibt, der üblicherweise in jeder Stufe verwendet wird, definieren Sie ihn vor dem ersten FROM.
ARG YOUR_ARG="Default value"
FROM alpine:latest as first_stage
#ARG muss für jede verwendete Stufe deklariert werden.
ARG YOUR_ARG
RUN echo "1st stage: ${YOUR_ARG}"
FROM alpine:latest as second_stage
#ARG muss für jede verwendete Stufe deklariert werden.
ARG YOUR_ARG
RUN echo "2nd stage: ${YOUR_ARG}"
In mehrstufigen Builds scheint der Umfang von ARG und ENV pro Stufe begrenzt zu sein. Wussten Sie alle? Ich wusste es nicht, bis mir klar wurde, dass ich mich in der Phase der von mir erstellten Docker-Datei nicht auf den Wert von ARG beziehen konnte.
Laut diesem Kommentar
Correct, Dockerfile instructions, including ENV vars and ARG are scoped per build-stage, and will not be preserved in the next stage; this is by design. You can, however, set a global ARG (set before the first build-stage), and use that value in each build-stage; Dockerfile-Anweisungen, einschließlich ENV und ARG, gelten für jede Build-Phase und werden nicht auf die nächste Phase übertragen. Dies ist, was es beabsichtigt ist. Wenn Sie jedoch das globale ARG (definiert vor der ersten Erstellungsphase) verwenden, können Sie diesen Wert für jede Erstellungsphase nutzen.
... anscheinend ... "Ja wirklich?"
Es wurde auch fest im offiziellen Dokument aufgeführt.
Der variable Bereich der ARG-Anweisung gilt bis zum Ende der Erstellungsphase, in der sie definiert ist. Wenn Sie ARG in mehreren Erstellungsphasen verwenden möchten, müssen Sie die ARG-Anweisung einzeln angeben.
Als ich das Dokument zum ersten Mal las, hatte ich das Gefühl, ich dachte: "Ahhhhh, ich habe es vollständig verstanden", ohne die Bedeutung der Erstellungsphase zu kennen. .. ..
Mal sehen, wie ARG in einem mehrstufigen Build funktioniert.
Zum Zeitpunkt des Schreibens dieses Artikels haben wir den Vorgang mit den folgenden Versionen bestätigt.
# docker --version
Docker version 18.09.1, build 4c52b90
Dockerfile
Die in dieser Überprüfung verwendete Docker-Datei lautet wie folgt.
Dockerfile
#ARG1 deklariert global und legt globale Standardwerte fest.
ARG ARG1="arg1 global default value"
#ARG2 deklariert global, legt jedoch keinen globalen Standardwert fest.
ARG ARG2
#ARG3 deklariert nicht global.
# ARG ARG3
FROM alpine:latest as first_stage
# first_In der Phase wird jedes ARG deklariert und der Standardwert im Bereich festgelegt.
ARG ARG1="arg1 first stage value"
ARG ARG2="arg2 first stage value"
ARG ARG3="arg3 first stage value"
RUN echo -e "first_stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
FROM alpine:latest as second_stage
# second_In der Phase wird jedes ARG deklariert, es wird jedoch kein Standardwert im Bereich festgelegt.
ARG ARG1
ARG ARG2
ARG ARG3
RUN echo -e "second_stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
FROM alpine:latest as third_stage
# third_Deklarieren Sie zu diesem Zeitpunkt nicht alle ARGs.
# ARG ARG1
# ARG ARG2
# ARG ARG3
RUN echo -e "third_stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
Jedes ARG wird wie folgt eingestellt.
ARG Name | die Einstellungen |
---|---|
ARG1 | Als globales ARG festlegen. Geben Sie auch den Standardwert an. |
ARG2 | Als globales ARG festlegen. Es ist kein Standardwert angegeben. |
ARG3 | Nicht als globales ARG festlegen. |
Zusätzlich wird jede Stufe wie folgt eingestellt.
Künstlername | die Einstellungen |
---|---|
first_stage | Deklarieren Sie jedes ARG. Stellen Sie den Standardwert in der Stufe ein. |
second_stage | Deklarieren Sie jedes ARG. Stellen Sie den Standardwert nicht in der Stufe ein. |
third_stage | Deklarieren Sie ARG nicht. |
--build-arg
Build ohne AngabeVersuchen Sie beim Erstellen von Docker Image, ohne den Wert mit "--build-arg" anzugeben.
# docker build . --no-cache
Sending build context to Docker daemon 14.85kB
...snip...
Step 7/14 : RUN echo -e "1st stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in 2bbe78634ee8
first_stage:
ARG1=arg1 first stage value
ARG2=arg2 first stage value
ARG3=arg3 first stage value
...snip...
Step 12/14 : RUN echo -e "2nd stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in 0c28af93ea9b
second_stage:
ARG1=arg1 global default value
ARG2=
ARG3=
...snip...
Step 14/14 : RUN echo -e "3rd stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in cbca9ed88691
third_stage:
ARG1=
ARG2=
ARG3=
...snip...
--build-arg
Build mit SpezifikationVersuchen Sie nun, mit dem durch --build-arg
angegebenen Wert zu erstellen.
# docker build --build-arg ARG1="build arg1 value" --build-arg ARG2="build arg2 value" --build-arg ARG3="build arg3 value" . --no-cache
Sending build context to Docker daemon 14.85kB
...snip...
Step 7/14 : RUN echo -e "1st stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in 10b37c5a524b
first_stage:
ARG1=build arg1 value
ARG2=build arg2 value
ARG3=build arg3 value
...snip...
Step 12/14 : RUN echo -e "2nd stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in e70e3ff9fe9b
second_stage:
ARG1=build arg1 value
ARG2=build arg2 value
ARG3=build arg3 value
...snip...
Step 14/14 : RUN echo -e "3rd stage:\n\tARG1=${ARG1}\n\tARG2=${ARG2}\n\tARG3=${ARG3}"
---> Running in e675e8f648e8
third_stage:
ARG1=
ARG2=
ARG3=
...snip...
--build-arg
angegebenen Werte. Dies steht im Einklang mit den Beschreibungen in ARG-Standardeinstellungen für offizielles Dokument. Der durch "--build-arg" angegebene Wert hat Vorrang vor dem globalen Standardwert und dem Standardwert in der Phase.--build-arg
[Hohe Priorität]Das ist es.
Dies ist eine Werbung für das Projekt, die mich dazu veranlasste, das Verhalten von ARG im mehrstufigen Build zu bemerken.
Lassen Sie uns Minecrafts Bedrock Server einfach bedienen! Es ist ein Projekt in diesem Sinne. Minecraft wird gelegentlich aktualisiert, aber der Client wird meistens selbst aktualisiert, aber Bedrock Server wird nicht automatisch aktualisiert, indem die neue Version manuell heruntergeladen und die Zip-Datei extrahiert wird, um die Binärdatei zu extrahieren. Ich musste es ersetzen und den Dienst neu starten ... oder so. Dieses Projekt muss nur einmal eingerichtet werden und der Bedrock Server wird automatisch aktualisiert! Docker wird übrigens zum Erstellen von Bedrock Server verwendet, damit die Umwelt nicht verschmutzt wird!
Vielen Dank!
Wirklich gemacht.
Recommended Posts