Docker-Inspektion, Teil 3

Images und Container in Docker

| Autor / Redakteur: Thomas Drilling / Ulrike Ostler

Docker hat die Virtualisierung auf den Kopf gestellt. Autor und IT-Berater Thomas Drilling erläutert, wie Docker aufgebaut ist.
Docker hat die Virtualisierung auf den Kopf gestellt. Autor und IT-Berater Thomas Drilling erläutert, wie Docker aufgebaut ist. (Bild: gemeinfrei - MrsBrown/Pixabay/Docker.com / CC0)

Docker-Container werden stets aus vorgefertigten Images instanziiert und sind damit eine nur lesbare Laufzeit-Inkarnation eines Image. Der Zusammenhang ist für die Arbeitsweise von Docker essentiell.

Der Docker-Client interagiert über die libcontainer-Schnittstelle mit dem Docker-Daemon und stellt elementarte Befehle zum Erstellen, Starten, Stoppen und Terminieren von Containern, dem Bauen von neuen Images oder dem erzeugen eines Images aus einen Container, sowie dem Starten von Applikationen „im“ Containern über eine Kommandoschnittstelle bereit.

Der Docker-Client interagiert über die "libcontainer"-Schnittstelle mit dem Docker-Daemon und stellt elementarte Befehle bereit.
Der Docker-Client interagiert über die "libcontainer"-Schnittstelle mit dem Docker-Daemon und stellt elementarte Befehle bereit. (Bild: Thomas Drlling)

Die am häufigsten benötigten Docker-Kommandos sind: docker …. run, create, exec, stopp, kill, build, deploy und commit. Die jeweilige Funktionsweise und Wirkung setzt ein genaues Verständnis der Zusammenhänge zwischen Container und Image voraus.

Der Schichtbetrieb

Jeder Container wird aus einem eigenen Image mit eigenen Dateisystem heraus instanziiert. Einer der wichtigsten Gründe, warum Docker-Container-Technologien, wie sie mit „LXC“, „OpenVZ“ oder „Solaris Zones“ schon lange bekannt waren, liegt in diesem Prinzip begründet und der Tatsache, dass Docker mit dem Docker Hub ein zentrales Image-Repository aufgebaut hat und mitsamt der Tools und Ökosystem pflegt.

Basis für das Instanziieren eines neuen Containers ist daher stets ein Image. Ist der Nutzer mit einem kostenlos erstellbaren Docker-Hub-Konto mit dem Repository verbunden und hat das gewünschte Image lokalisiert, kann er mit „docker run ....“ einen neuen Container auf dessen Basis instanziieren. Wahlweise kann er das Image auch vorab mit „docker pull …“ vorab in sein lokales Docker-Repository herunterladen.

Es gibt eine ganze Reihe von Repositories, die für Docker-Images genutzt werden können.
Es gibt eine ganze Reihe von Repositories, die für Docker-Images genutzt werden können. (Bild: Thomas Drilling)

Docker-Images sind dabei in Schichten organisiert, wobei auf unterste Ebene stets ein Betriebssystem-Image zum Einsatz kommt, wie von „Ubuntu“, „CentOS“ oder „Busybox“, welche den darauf aufbauenden Applikations-Layern die jeweils passende Laufzeitumgebung mitgeben. Wurde aus einem Basis-Image ein Container instanziiert, kann der Nutzer mit „docker commit …“ jederzeit neue „Momentaufnahmen“ in Form von neuen Images ableiten, die den aktuellen Zustand des Systems wiederspiegeln.

Vom Image zum Container und zurück

Startet der Nutzer mit einem CentOS-Basis-Betriebssystem-Container kann er zur Laufzeit weitere Apps wie „Python“ installieren; der Container spiegelt dann ein CentOS mit Python wieder. Der Container selbst ist die „Laufzeit-Reinkarnation“ des aktuellen Images zum Zeitpunkt „t“.

Ein neues Images (Basis-Betriebssystem + Python) hätte dann eine zweischichtige Architektur. Da ein Container keinen persistenten Speicher hat, bedarf es eines Dateisystems mit Journaling/Copy-On-Write-Support, um aktuelle Änderungen in einer Art Snapshot-Layer an oberster Position der geschichteten Dateisystem-Architektur zu verankern. Dabei kann allerdings immer nur die Änderungen in Bezug auf den Basis-Layer effektiv gespeichert werden.

Die Zusammensetzung aus verschiedenen Schichten.
Die Zusammensetzung aus verschiedenen Schichten. (Bild: Thomas Drilling)

Daraus ergeben sich die folgenden Zusammenhänge:

  • Docker-Images sind Read-Only-Templates, aus denen Container instanziiert werden.
  • Docker-Images bestehen aus einem oder mehreren Dateisystem-Layern, von denen der jeweils Obere auf dem Unterliegenden aufsetzt. Docker verwendet Union Files Systems (UFS) zum Bauen von Images
  • Jedes Update eines Images fügt einen neuen Layer hinzu, anstatt jedes Mal das gesamte Image neu zu bauen, wobei der oberste Layer (writeable Layer) als Snapshot fungiert.
  • Images können von verschiedene Containern zu gleichen Zeit geteilt werden
  • Daraus ergibt sich die Gleichung: Container = Image + writeable Layer

Der Build-Prozess

Jede Änderung an einem Container zur Laufzeit wie das Installieren zusätzlicher Software findet stets auf Basis dieses oberen „writeable containers“ statt. Beendet der Nutzer einen Container ohne zwischenzeitlich ein neues Image gebaut zu haben, verliert er sämtliche Änderungen und fällt auf den Stand des Basis-Images zurück, da der writeable container wie ein Snapshot funktioniert.

Schema eines Build-Prozesses mit Docker.
Schema eines Build-Prozesses mit Docker. (Bild: Thomas Drilling)

Selbstverständlich finden sich in Docker Hub nicht nur OS-Images, sondern überwiegend mehrschichtige Applikations-Images. Man kann Images zudem privat- oder öffentlich hosten und versionieren. Images lassen sich (anstatt mit „commit“ aus einem Container) mit dem Kommando „docker build …“ auch direkt from scratch bauen.

Das ist auch notwendig, wenn man Images mit der Community teilen möchte. Andernfalls könnte man nur Basis-Images frei zur Verfügung stellen und müssten zum Erhalten eines Applikations-Containers jeweils eine Art Bauplan veröffentlichen der beschreibt, welche Pakete im jeweiligen Layer installiert wurden. Genau das geschieht mit Hilfe des docker-build-Befehls, der durch das jeweilige Docker-Manifest File gesteuert wird.

Das Docker-File ist zunächst einmal eine Textdatei.
Das Docker-File ist zunächst einmal eine Textdatei. (Bild: Thomas Drilling)

Zur Erinnerung: Jeder Layer ist Teil eines Images und enthält ausgehend vom Base-Image einen Befehl oder eine Datei, die dem Image hinzugefügt wurde. Anhand der Layer lässt sich die ganze Historie des Images nachvollziehen.

Das Docker-File ist eine Textdatei, die anhand verschiedener Befehlen beschreibt wie das finale Image entsteht. Das Docker-File legt für jeden einzelnen (docker-run)-Befehl einen einzelnen Layer an, wodurch bis zum finalen Image durchaus mehrere so genannte Intermediate-Container entstehen können und auch wieder verworfen werden. Für jedes Image auf Docker-Hub gibt es eine Referenz auf das zugehörige Docker-File, die direkt auf „Github“ verweist.

Was meinen Sie zu diesem Thema?

Schreiben Sie uns hier Ihre Meinung ...
(nicht registrierter User)

Zur Wahrung unserer Interessen speichern wir zusätzlich zu den o.g. Informationen die IP-Adresse. Dies dient ausschließlich dem Zweck, dass Sie als Urheber des Kommentars identifiziert werden können. Rechtliche Grundlage ist die Wahrung berechtigter Interessen gem. Art 6 Abs 1 lit. f) DSGVO.
Kommentar abschicken
copyright

Dieser Beitrag ist urheberrechtlich geschützt. Sie wollen ihn für Ihre Zwecke verwenden? Infos finden Sie unter www.mycontentfactory.de (ID: 45516293 / Virtualisierung)