Wie kann man Docker-Compose dazu bringen, Container immer aus frischen Bildern neu zu erstellen?

198

Meine Docker-Images basieren auf einem Jenkins CI-Server und werden in unsere private Docker-Registrierung übertragen. Mein Ziel ist es, Umgebungen mit Docker-Compose bereitzustellen, die immer den ursprünglich erstellten Status der Images starten.

Ich verwende derzeit Docker-Compose 1.3.2 sowie 1.4.0 auf verschiedenen Computern, aber wir haben zuvor auch ältere Versionen verwendet.

Ich habe immer die docker-compose pull && docker-compose up -dBefehle verwendet, um die neuen Bilder aus der Registrierung abzurufen und sie zu starten. Ich glaube, mein bevorzugtes Verhalten funktionierte bis zu einem bestimmten Zeitpunkt wie erwartet, aber seitdem wurden docker-compose upzuvor gestoppte Container erneut ausgeführt, anstatt jedes Mal die ursprünglich erstellten Images zu starten.

Gibt es eine Möglichkeit, dieses Verhalten loszuwerden? Könnte dies eine sein, die in der Konfigurationsdatei docker-compose.yml verkabelt ist, um nicht bei jedem Aufruf etwas in der Befehlszeile "nicht zu vergessen"?

ps. Ich würde nicht nur einen Weg finden, mein Ziel zu erreichen, sondern auch gerne etwas mehr über den Hintergrund dieses Verhaltens erfahren. Ich denke, die Grundidee von Docker ist es, eine unveränderliche Infrastruktur aufzubauen. Das derzeitige Verhalten von Docker-Compose scheint einfach mit diesem Ansatz in Konflikt zu geraten. Oder vermisse ich hier einige Punkte?

Kristof Jozsa
quelle

Antworten:

232

docker-compose up --force-recreateist eine Option, aber wenn Sie es für CI verwenden, würde ich den Build mit starten, docker-compose rm -fum die Container und Volumes zu stoppen und zu entfernen (dann folgen Sie ihm mit Pull und Up).

Das benutze ich:

docker-compose rm -f
docker-compose pull
docker-compose up --build -d
# Run some tests
./tests
docker-compose stop -t 1

Der Grund, warum Container neu erstellt werden, besteht darin, eventuell verwendete Datenmengen beizubehalten (und dies führt auch zu upeiner erheblichen Beschleunigung).

Wenn Sie CI machen, wollen Sie das nicht. Wenn Sie also alles entfernen, sollten Sie das wollen, was Sie wollen.

Update: Verwendung, up --builddie in docker-compose1.7 hinzugefügt wurde

Dnephin
quelle
1
Ja, genau das mache ich auch in CI. Ich bin mir nicht sicher, warum ich das nicht erwähnt habe ...
Adrian Mouat
@dnephin docker-compose run -dexistiert nicht? Du willst docker-compose up -dnein sagen ?
Guillaume Vincent
2
Wenn Sie laufen, docker-compose pullbevor docker-compose rm -fSie noch mehr Zeit sparen können
stephanlindauer
2
Was macht das Flag -d am Ende?
David J. Davis
3
"-d Freistehender Modus: Container im Hintergrund
ausführen
135

Die einzige Lösung, die für mich funktioniert hat, war dieser Befehl:

docker-compose build --no-cache

Dadurch wird automatisch ein neues Image aus dem Repo abgerufen und die vorgefertigte Cache-Version mit den zuvor verwendeten Parametern wird nicht verwendet.

Davidbonachera
quelle
1
Außerdem kann es unter Windows 10 hilfreich sein, den DNS-Server in den Einstellungen von Automatisch auf Fest oder von Fest auf Automatisch einzustellen.
Qräbnö
2
Arbeitete für mich am OS X-Erstellen mit Docker-Comopse-Version 2.
RoboBear
1
Arbeitete unter OS X Docker.
HelloWorld
55

Nach der aktuellen offiziellen Dokumentation gibt es eine Verknüpfung, die Container, Netzwerke, Volumes und Images, die von up erstellt wurden, stoppt und entfernt. Wenn sie bereits gestoppt oder teilweise entfernt wurden usw., reicht dies ebenfalls aus:

docker-compose down

Wenn Sie neue Änderungen an Ihren Bildern oder Docker-Dateien vorgenommen haben, verwenden Sie:

docker-compose build --no-cache

Schließlich:docker-compose up

In einem Befehl: docker-compose down && docker-compose build --no-cache && docker-compose up

Victor Timoftii
quelle
2
docker-compose build --no-cachewird nur benötigt, wenn Änderungen an Docker-Dateien vorgenommen wurden.
Victor Timoftii
In der Tat, Victor. Vielen Dank! Ich dachte, dass es auch nach dem Aktualisieren eines Moduls / einer Anwendung notwendig ist, die beim Starten des Containers ausgeführt wird. In diesen Fällen ist es vor dem Ausführen docker-compose uperforderlich, die Dienste mit neu zu erstellen docker-compose build.
ivanleoncz
18

Sie können --force-recreatean übergeben docker compose up, die frische Behälter verwenden sollten.

Ich denke, der Grund für die Wiederverwendung von Containern besteht darin, Änderungen während der Entwicklung beizubehalten. Beachten Sie, dass Compose mit Volumes etwas Ähnliches macht, das auch zwischen der Neuerstellung von Containern bestehen bleibt (ein neu erstellter Container wird an die Volumes seines Vorgängers angehängt). Dies kann beispielsweise hilfreich sein, wenn Sie einen Redis-Container als Cache verwenden und den Cache nicht jedes Mal verlieren möchten, wenn Sie eine kleine Änderung vornehmen. Zu anderen Zeiten ist es nur verwirrend.

Ich glaube nicht, dass Sie dies auf irgendeine Weise aus der Compose-Datei erzwingen können.

Wahrscheinlich kollidiert es mit unveränderlichen Infrastrukturprinzipien. Das Gegenargument ist wahrscheinlich, dass Sie Compose (noch) nicht in der Produktion verwenden. Ich bin mir auch nicht sicher, ob ich damit einverstanden bin, dass unveränderliche Infrastruktur die Grundidee von Docker ist, obwohl dies sicherlich ein guter Anwendungsfall / Verkaufsargument ist.

Adrian Mouat
quelle
Danke für die Antwort. Ich denke, es wäre wirklich nützlich, es auf Konfigurationsebene zu erzwingen, z. um es für einen Datenbankcontainer zu erzwingen und die Neuerstellung für die App-Container standardmäßig zu deaktivieren.
Kristof Jozsa
8
--force-recreatefunktioniert bei mir nicht ... Bild wird nicht gezogen, obwohl es eine neuere Version gibt ...
lisak
1
@lisak Ich habe nie gesagt, dass es neue Bilder gezogen hat. Das tut es nicht. Es werden nur neue Container mit dem lokal verfügbaren Image gestartet. Sie müssen Docker Pull manuell ausführen.
Adrian Mouat
2
docker-compose up --build

ODER

docker-compose build --no-cache
flgn
quelle
1
Wenn möglich, bemühen Sie sich, zusätzliche Erklärungen anstelle von nur Code bereitzustellen. Solche Antworten sind in der Regel nützlicher, da sie Mitgliedern der Community und insbesondere neuen Entwicklern helfen, die Gründe für die Lösung besser zu verstehen, und dazu beitragen können, dass keine weiteren Fragen beantwortet werden müssen.
Rajan
-10
$docker-compose build

Wenn es etwas Neues gibt, wird es wieder aufgebaut.

Mathias Asberg
quelle