Dies ist nun möglich, seit Docker 19.03.0 im Juli 2019 „Custom Build Outputs“ eingeführt hat. Sehen Sie sich die offiziellen Dokumente zu benutzerdefinierten Build-Ausgaben an.
Um benutzerdefinierte Build-Ausgaben aus dem Build-Image während des Build-Prozesses in den Host zu aktivieren, müssen Sie das BuildKit aktivieren Dies ist eine neuere empfohlene abwärtskompatible Methode für die Engine, um die Build-Phase durchzuführen. Informationen zum Aktivieren von BuildKit finden Sie in den offiziellen Dokumenten.
Dies kann auf zwei Arten erfolgen:
- Setzen Sie die Umgebungsvariable
DOCKER_BUILDKIT=1
, oder - Legen Sie es standardmäßig in der Docker-Engine fest, indem Sie
"features": { "buildkit": true }
hinzufügen in das Stammverzeichnis der Konfigurationsdatei json.
Aus den offiziellen Dokumenten zu benutzerdefinierten Build-Ausgaben:
Mit benutzerdefinierten Exportern können Sie die Build-Artefakte als Dateien im lokalen Dateisystem statt als Docker-Image exportieren, was für die Generierung lokaler Binärdateien, Codegenerierung usw. nützlich sein kann.
...
Der lokale Exporter schreibt die resultierenden Build-Dateien in ein Verzeichnis auf der Clientseite. Der tar-Exporter ist ähnlich, schreibt die Dateien jedoch als einen einzigen Tarball (.tar).
Wenn kein Typ angegeben ist, ist der Wert standardmäßig das Ausgabeverzeichnis des lokalen Exportprogramms.
...
Die Option --output exportiert alle Dateien aus der Zielstufe. Ein gängiges Muster für den Export nur bestimmter Dateien besteht darin, mehrstufige Builds durchzuführen und die gewünschten Dateien mit COPY --from.
in eine neue Arbeitsphase zu kopierenz.B. ein Beispiel-Dockerfile
FROM alpine:latest AS stage1
WORKDIR /app
RUN echo "hello world" > output.txt
FROM scratch AS export-stage
COPY --from=stage1 /app/output.txt .
Laufen
DOCKER_BUILDKIT=1 docker build --file Dockerfile --output out .
Das Ende der Ausgabe ist:
=> [export-stage 1/1] COPY --from=stage1 /app/output.txt .
0.0s
=> exporting to client
0.1s
=> => copying files 45B
0.1s
Dies erzeugt eine lokale Datei out/output.txt
die von RUN
erstellt wurde Befehl.
$ cat out/output.txt
hello world
Alle Dateien werden von der Zielstufe ausgegeben
Die --output
Option exportiert alle Dateien aus der Zielstufe. Verwenden Sie also eine Nicht-Scratch-Stufe mit COPY --from
bewirkt, dass überflüssige Dateien in die Ausgabe kopiert werden. Die Empfehlung ist, eine Scratch-Stage mit COPY --from
zu verwenden .
Das Kopieren von Dateien "aus dem Dockerfile" auf den Host ist nicht unterstützt. Das Dockerfile ist nur ein Rezept, das angibt, wie ein Image erstellt wird.
Beim Erstellen haben Sie die Möglichkeit, Dateien vom Host auf das Image zu kopieren, das Sie erstellen (mit dem COPY
Direktive oder ADD
)
Sie können auch Dateien aus einem Container kopieren (ein Bild, das docker run
'd) zum Host mit docker cp (eigentlich kann der cp auch vom Host in den Container kopieren)
Wenn Sie einige Dateien, die möglicherweise während des Builds generiert wurden, an Ihren Host zurückgeben möchten (wie zum Beispiel das Aufrufen eines Skripts, das SSL generiert), können Sie einen Container ausführen, einen Ordner von Ihrem Host mounten und cp-Befehle ausführen.
Siehe zum Beispiel dieses getcrt-Skript.
docker run -u root --entrypoint=/bin/sh --rm -i -v ${HOME}/b2d/apache:/apache apache << COMMANDS
pwd
cp crt /apache
cp key /apache
echo Changing owner from \$(id -u):\$(id -g) to $(id -u):$(id -u)
chown -R $(id -u):$(id -u) /apache/crt
chown -R $(id -u):$(id -u) /apache/key
COMMANDS
Alles zwischen COMMANDS
sind Befehle, die auf dem Container ausgeführt werden, einschließlich cp
diejenigen, die auf den Host ${HOME}/b2d/apache
kopieren Ordner, der im Container als /apache
gemountet ist mit -v ${HOME}/b2d/apache:/apache
.
Das bedeutet jedes Mal, wenn Sie irgendetwas auf /apache
kopieren im Container kopierst du eigentlich ${HOME}/b2d/apache
hinein auf dem Host!
Obwohl es nicht direkt über Dockerfile
unterstützt wird Funktion können Sie Dateien aus einem erstellten Docker-Image kopieren.
containerId=$(docker create example:latest)
docker cp "$containerId":/source/path /destination/path
docker rm "$containerId"