Direkt zum Inhalt

Docker Buildx: Wie man plattformübergreifende Container-Images erstellt

Erfahre, wie Docker Buildx die herkömmliche Containererstellung um Multiplattform-Unterstützung, fortschrittliche Caching-Strategien und Leistungsoptimierungen erweitert. Dieser Leitfaden deckt alles von grundlegenden Konzepten bis hin zu fortgeschrittenen Techniken ab.
Aktualisierte 15. Mai 2025  · 14 Min. Lesezeit

Das Erstellen von Containern für mehrere Plattformen klingt einschüchternd und zeitaufwändig, aber du wirst sehen, dass das gar nicht so ist.

Der Befehl docker buildx löst diese Herausforderung, indem er die Build-Fähigkeiten von Docker um fortschrittliche Funktionen wie die Erstellung von Multiplattform-Images, verbessertes Caching und parallele Build-Verarbeitung erweitert. Es integriert die nächste Generation der Build-Engine BuildKit direkt in das Docker CLI. Mit dem Befehl buildx erstellst du kleinere, schnellere und sicherere Container-Images, ohne ein komplett neues Toolset zu lernen.

In den letzten Jahren ist Buildx für beste DevOps-Praktiken und die Entwicklung von Cloud-nativen Anwendungen mehr oder weniger unverzichtbar geworden. Sie rationalisiert CI/CD-Pipelines und hilft dir und deinem Team, Anwendungen konsistent über verschiedene Bereitstellungsziele hinweg zu liefern, von ARM-basierten IoT-Geräten bis hin zu Cloud-Serverfarmen.

> Neu bei Docker? Mit unserem praktischen Leitfaden für Anfänger kannst du im Handumdrehen loslegen.

In diesem Artikel führe ich dich durch die Techniken für Anfänger und Fortgeschrittene docker buildx.

Docker Buildx verstehen

Wahrscheinlich verwendest du bereits Docker, sodass du den Standardbefehl docker build kennst. Früher oder später wird es sich jedoch einschränkend anfühlen, vor allem, wenn deine Projekte komplexer werden.

> Docker Buildx geht davon aus, dass du Docker installiert hast. Wenn du das nicht tust und mit gLinux arbeitest, befolge diese Anleitung für eine einfache Installation.

Docker Buildx bietet dir eine verbesserte Build-Erfahrung, die mit deinem vorhandenen Wissen arbeitet. Es ist kein separates Tool, das du installieren musst - es ist seit Version 19.03 bereits mit Docker Desktop und Engine gebündelt. Buildx nutzt unter der Haube BuildKit, den Docker-Builder der nächsten Generation, der die Art und Weise, wie Images erstellt werden, umschreibt. Du wirst feststellen, dass schnellere Builds, kleinere Bilder und Unterstützung für zusätzliche Funktionen bietet.

Der Sprung von docker build zu docker buildx build mag klein erscheinen - es ist schließlich nur ein Wort - aber die Möglichkeiten, die du dadurch gewinnst, sind enorm.

Lass uns herausfinden, wie Buildx wirklich funktioniert und was es von den herkömmlichen Buildern unterscheidet.

Architektonische Grundlagen von Buildx

Der Zauber von Buildx liegt in seinem intelligenten Client-Server-Design.

Wenn du einen Buildx-Befehl ausführst, verwendest du das Docker CLI als Client, der mit dem BuildKit-Daemon kommuniziert - der Serverkomponente, die die schwere Arbeit erledigt. Durch diese Trennung kann BuildKit Dinge tun, die der Legacy-Builder nicht kann, z.B. parallel statt sequentiellausführen. Deine Dockerfile-Anweisungen müssen nicht mehr nacheinander ausgeführt werden, was die Erstellungszeiten bei unabhängigen Phasen erheblich verkürzt.

Das Client-Server-Modell ermöglicht auch eine Remote-Build-Ausführung. Du kannst dein lokales Docker CLI auf eine entfernte BuildKit-Instanz richten, die überall läuft - auf einem leistungsfähigen Build-Server, in der Cloud oder sogar in einem Kubernetes-Cluster. Diese Flexibilität bedeutet, dass du die Ressourcen deines Laptops nicht für umfangreiche Builds beanspruchen musst und dir keine Gedanken über Kompatibilitätsprobleme mit der Architektur machen musst.

Das modulare Design von BuildKit ermöglicht es dir auch, verschiedene Frontend-Parsereinzubauen . Die Dockerfile-Syntax ist der Standard, aber du kannst auch andere Build-Definitionsformate verwenden, wenn sie besser zu deinem Arbeitsablauf passen.

Prozessablauf erstellen

Wenn du docker buildx build aufrufst, wählt das CLI zunächst eine Builder-Instanz aus, entweder die Standardinstanz oder eine, die du angegeben hast. Dein Build-Kontext und dein Dockerfile werden an den BuildKit-Daemon gesendet, der die Anweisungen analysiert und einen gerichteten azyklischen Graphen (DAG) mit Build-Schritten erstellt. Im Gegensatz zum Legacy-Builder, der jede Anweisung sequenziell abarbeitet, analysiert BuildKit diesen Graphen, um festzustellen, welche Schritte parallel ausgeführt werden können.

Der Builder führt diese Schritte dann mit effizienten Caching-Algorithmen aus, die viel intelligenter sind als der alte schichtenbasierte Cache. BuildKit verfolgt die genauen Eingaben und Ausgaben jedes Schritts, wodurch unnötige Neuaufbauten vermieden werden, wenn sich nichts Relevantes geändert hat. Es unterstützt auch die Verteilung des Builds auf mehrere Worker Nodes für eine noch schnellere Verarbeitung.

Nach der Erstellung kann Buildx die Ergebnisse in verschiedenen Formaten exportieren, nicht nur als Docker-Images. Du kannst in OCI-Formate, lokale Verzeichnisse oder Tarballs ausgeben oder die Image-Erstellung ganz überspringen, wenn du den Build-Prozess nur testen willst.

Du hast Recht - dieser Abschnitt könnte definitiv von mehr praktischen Beispielen und Anschauungsmaterial profitieren, um zu zeigen, wie Buildx in der realen Welt funktioniert. Hier ist, wie ich es mit mehr Codebeispielen und Vorschlägen für Bilder verbessern würde:

Kernfunktionalität und Merkmale

Bei Docker Buildx geht es nicht nur darum, Images schneller zu erstellen, obwohl es das definitiv tut. Es geht darum, zu erweitern, was mit deinen Build-Pipelines möglich ist.

Lass uns in die herausragenden Funktionen eintauchen, die Buildx für dein nächstes Projekt interessant machen.

> Suchst du nach einem Docker-Projekt ideas? Diese 10 werden dein DevOps-Portfolio auf Vordermann bringen.

Verwendete Python-Anwendung

Für diesen Artikel habe ich eine einfache Python-Flask-Anwendung erstellt. Erstelle dazu 3 Dateien - app.py, requirements.txt und Dockerfile.

Das sind die Inhalte für jeden:

app.py

from flask import Flask, render_template_string
import platform
import socket
import psutil
import datetime

app = Flask(__name__)


@app.route("/")
def home():
    html = """
    <!DOCTYPE html>
    <html>
      <head>
        <title>Docker Buildx Python Demo</title>
        <style>
          body {
            
            max-width: 800px;
            
            
          }
          .container {
            border: 1px solid #ddd;
            border-radius: 5px;
            
            background-
          }
          .info {
            
          }
          .platform {
            font-weight: bold;
            
          }
        </style>
      </head>
      <body>
        <h1>Docker Buildx Multi-Platform Demo (Python)</h1>
        <div class="container">
          <div class="info">Hostname: {{ hostname }}</div>
          <div class="info">Platform: <span class="platform">{{ os_platform }} ({{ architecture }})</span></div>
          <div class="info">CPUs: {{ cpu_count }}</div>
          <div class="info">Total Memory: {{ memory_mb }} MB</div>
          <div class="info">Server Time: {{ server_time }}</div>
        </div>
      </body>
    </html>
    """
    return render_template_string(
        html,
        hostname=socket.gethostname(),
        os_platform=platform.system(),
        architecture=platform.machine(),
        cpu_count=psutil.cpu_count(),
        memory_mb=round(psutil.virtual_memory().total / (1024 * 1024)),
        server_time=datetime.datetime.now().isoformat(),
    )


if __name__ == "__main__":
    app.run(host="0.0.0.0", port=5000)

requirements.txt

flask==3.1.0
psutil==7.0.0

Dockerfile

FROM python:3.13-slim

WORKDIR /app

COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

COPY app.py .

EXPOSE 5000

CMD ["python", "app.py"]

Öffne anschließend ein neues Terminal-Fenster und navigiere zu dem Projektordner.

Multiplattform-Bildaufbau

Bilder zu erstellen, die auf verschiedenen CPU-Architekturen funktionieren, klingt wie ein Albtraum, aber Buildx macht es überraschend einfach.

Sieh dir diesen Befehl an:

docker buildx build --platform linux/amd64,linux/arm64 -t myapp:latest .

Bild 1 - Docker Buildx verwenden

Bild 1 - Docker Buildx verwenden

Kurz gesagt, kannst du damit Bilder für mehrere Architekturen gleichzeitig erstellen. Buildx hat dafür drei clevere Ansätze: Es kann QEMU für die Architekturemulation verwenden (damit kannst du ARM-Images auf einem x86-Rechner erstellen), sich mit nativen Builder Nodes für jede Zielplattform verbinden oder beide Methoden für optimale Leistung kombinieren. Das Ergebnis ist eine Multi-Architektur-Manifestliste - manchmal auch "Fat Manifest" genannt -, die Varianten deines Images für jede Plattform enthält.

Wenn du in verschiedenen Umgebungen wie AWS Graviton Instanzen, Raspberry Pi Clustern oder gemischten Infrastrukturen arbeitest, ist diese Unterstützung für mehrere Plattformen entscheidend.

Verbesserte Caching-Strategien

Buildx verändert die Art und Weise, wie Build-Caching funktioniert, komplett und macht deine Builds generell schneller.

Das System implementiert eine dreistufige Caching-Strategie, die über das einfache Layer-Caching herkömmlicher Docker-Builds hinausgeht:

  1. Inline-Cache-Einbettung: Erstens verwendet Buildx einen Inline-Cache, der in deine Bilder eingebettet ist. So kannst du zwischengespeicherte Ebenen aus früheren Builds auch in neuen Umgebungen nutzen.
  2. Lokaler Build-Cache: Zweitens unterstützt es einen lokalen Build-Cache, der intelligent verwaltet wird und auf den Eingaben der Build-Instruktionen basiert und nicht nur auf deren Reihenfolge.
  3. Registry-basiertes Caching: Drittens bietet es ein registry-basiertes Caching, mit dem du den Build-Cache auf mehreren Rechnern gemeinsam nutzen kannst - perfekt für CI/CD-Pipelines oder verteilte Teams.

Mit unserer Python-App wollen wir sehen, wie wir lokale Caching-Strategien nutzen können:

# Create a directory for local cache
mkdir -p buildx-cache

# First build - export cache to local directory
docker buildx build --cache-to type=local,dest=./buildx-cache -t myapp:latest .

# Make a small change to app.py
echo "# Small comment change" >> app.py

# Second build - use the local cache
docker buildx build --cache-from type=local,src=./buildx-cache -t myapp:latest .

Der zweite Build wird viel schneller sein, weil er die zwischengespeicherten Schichten des ersten Builds wiederverwendet.

Abbildung 2 - Lokale Caching-Strategien

Abbildung 2 - Lokale Caching-Strategien

Du kannst auch das Inline-Caching nutzen, bei dem die Cache-Metadaten in das Bild selbst eingebettet werden:

docker buildx build --cache-to type=inline -t myapp:latest .

Du kannst diese Cache-Backends mit einfachen Flags wie --cache-to und --cache-from konfigurieren, die auf lokale Verzeichnisse, Registry-Repositories oder sogar spezielle Cache-Dienste verweisen. Diese Flexibilität bedeutet, dass deine Builds in verschiedenen Umgebungen schnell bleiben, ohne die Reproduzierbarkeit zu beeinträchtigen.

Sicherheitsmerkmale

Buildx enthält Tools, die Sicherheitsbedenken aus deinen Gedanken verbannen.

Angenommen, deine Python-App muss während des Build-Prozesses auf eine Wetter-API zugreifen. Anstatt deinen API-Schlüssel in der Dockerdatei zu kodieren, kannst du Build Secrets verwenden:

# Store your API key in a local file
echo "abc123yourweatherapikey" > ./api_key.txt

# Build with the secret
docker buildx build --secret id=weather_api_key,src=./api_key.txt -t myapp:latest .

In deinem Dockerfile kannst du dann nur bei Bedarf auf das Geheimnis zugreifen:

FROM python:3.13-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY app.py .
# Create a config file using the secret at build time
RUN --mount=type=secret,id=weather_api_key \
    echo "WEATHER_API_KEY=$(cat /run/secrets/weather_api_key)" > .env
EXPOSE 5000
CMD ["python", "app.py"]

Du kannst überprüfen, dass der API-Schlüssel nicht im endgültigen Bild enthalten ist, indem du den Bildverlauf überprüfst oder indem du ihn ausführst:

docker run --rm myapp:latest cat .env

Abbildung 3 - Verwaltung von Umgebungsvariablen

Abbildung 3 - Verwaltung von Umgebungsvariablen

In deinem app.py könntest du den API-Schlüssel wie folgt laden:

import os
from dotenv import load_dotenv

load_dotenv()  # Load variables from .env file
api_key = os.getenv("WEATHER_API_KEY", "")
# ...

Dieser Ansatz bedeutet, dass dein sensibler API-Schlüssel nur während des spezifischen Erstellungsschritts, in dem er benötigt wird, verfügbar ist, aber er wird in keiner der Bildebenen gespeichert. Jeder, der dein Bild abruft, wird nicht in der Lage sein, deinen API-Schlüssel zu extrahieren, selbst wenn er die Bildebenen untersucht.

Für zusätzliche Sicherheit kannst du auch temporäre Build-Container verwenden, die nach dem Build automatisch entfernt werden:

docker buildx build --secret id=weather_api_key,src=./api_key.txt --rm -t myapp:latest .

Das --rm Flag stellt sicher, dass alle Zwischencontainer, die während des Build-Prozesses erstellt werden, entfernt werden, um das Risiko von Zugangsdaten zu verringern.

Betriebliche Konfiguration

Um Buildx für deinen Arbeitsablauf einzurichten, brauchst du nur ein paar Befehle, aber wenn du die Optionen kennst, kannst du das Beste daraus machen.

Im Folgenden erfährst du, wie du Buildx in einer lokalen Umgebung so konfigurieren und verwalten kannst, dass es deinen speziellen Bedürfnissen entspricht.

Verwaltung der Builder-Instanzen

Docker Buildx verwendet das Konzept der "Builder" - getrennte BuildKit-Instanzen mit unterschiedlichen Fähigkeiten und Konfigurationen. Du kannst mehrere Bauherren für verschiedene Zwecke erstellen.

Schau zuerst nach, welche Bauherren du bereits hast:

docker buildx ls

Du wirst eine ähnliche Ausgabe wie diese sehen:

Bild 4 - Verfügbare Bauherren

Bild 4 - Verfügbare Bauherren

Um eine neue Builder-Instanz zu erstellen, führe die folgenden Befehle aus:

# Create a new builder
docker buildx create --name mybuilder

# Switch to using that builder
docker buildx use mybuilder

# Bootstrap the builder (start it)
docker buildx inspect --bootstrap

Du kannst überprüfen, ob es funktioniert mit:

# Check the status
docker buildx ls

Bild 5 - Wechsel zu einem Custom Builder

Bild 5 - Wechsel zu einem Custom Builder

Wenn du einen Builder entfernen musst, führe einfach Folgendes aus:

docker buildx rm mybuilder

Handhabung der Ausgabe

Buildx gibt dir flexible Möglichkeiten, was du mit den Bildern machen kannst, die du erstellst. Du kannst sie direkt in deinen lokalen Docker-Daemon laden, sie als Tarballs exportieren oder in einem lokalen Verzeichnis speichern.

Schauen wir uns an, wie wir diese Optionen mit unserer Python-App nutzen können:

# Load the image directly into Docker (default behavior)
docker buildx build --load -t myapp:latest .

# Export the image as a tarball
docker buildx build --output type=docker,dest=myapp.tar -t myapp:latest .

# Save the image contents to a local directory
docker buildx build --output type=local,dest=./image-output -t myapp:latest .

Nachdem du den Tarball exportiert hast, kannst du ihn mit in Docker laden:

docker load < myapp.tar

Abbildung 6 - Laden eines Images aus einem Tarball-Export

Abbildung 6 - Laden eines Images aus einem Tarball-Export

Die Ausgabe des lokalen Verzeichnisses ist besonders nützlich für die Überprüfung. Schauen wir uns an, was geschaffen wird:

ls -la ./image-output

Du wirst das Raw-Image-Dateisystem sehen:

Abbildung 7 - Inhalt des lokalen Verzeichnisses exportieren

Abbildung 7 - Inhalt des lokalen Verzeichnisses exportieren

Du kannst sogar bestimmte Build-Phasen ausführen, ohne ein endgültiges Image zu erstellen. Das ist praktisch zum Debuggen oder Testen von Build-Schritten:

# Create a multi-stage Dockerfile
cat > Dockerfile.multi << 'EOF'
FROM python:3.13-slim AS base
WORKDIR /app
COPY requirements.txt .

FROM base AS dev-deps
RUN pip install --no-cache-dir -r requirements.txt
RUN pip install pytest

FROM base AS prod-deps
RUN pip install --no-cache-dir -r requirements.txt

FROM prod-deps AS final
COPY app.py .
EXPOSE 5000
CMD ["python", "app.py"]
EOF

# Build only the dev-deps stage and export its filesystem
docker buildx build --file Dockerfile.multi --target dev-deps --output type=local,dest=./dev-deps-output .

Jetzt kannst du überprüfen, welche Pakete in der Entwicklungsumgebung installiert wurden:

cat ./dev-deps-output/usr/local/lib/python3.13/site-packages/pytest/__init__.py

Abbildung 8 - Dateiinhalte aus der Dev-deps-Phase

Abbildung 8 - Dateiinhalte aus der Dev-deps-Phase

Zusammenfassend lässt sich sagen, dass du mit diesen Ausgabeoptionen die volle Kontrolle darüber hast, wohin deine erstellten Bilder gehen, egal ob du lokal debuggst oder Bilder für dein Team vorbereitest.

Docker und Kubernetes beherrschen

Lerne in einem interaktiven Lernpfad die Leistungsfähigkeit von Docker und Kubernetes kennen, um Anwendungen in modernen Umgebungen zu entwickeln und einzusetzen.
Lernpfad kostenlos starten

Erweiterte Anwendungsfälle

Bis jetzt habe ich dir die grundlegenden Buildx-Befehle und Anwendungsfälle gezeigt. Buildx kann noch viel mehr, und einige der Funktionen sind mit dem klassischen Builder nicht umsetzbar.

Lass uns einige fortgeschrittene Techniken erforschen, um deinen Containerisierungs-Workflow auf die nächste Stufe zu heben.

Mehrstufige Bauoptimierung

Mehrstufige Builds sind eine der mächtigsten Funktionen von Docker, um effiziente Images zu erstellen, und Buildx macht sie noch besser.

Zur Veranschaulichung wollen wir eine optimierte Python-Anwendung mit mehreren Stufen erstellen:

# Dockerfile.optimized
FROM python:3.13-slim AS base
WORKDIR /app
COPY requirements.txt .

FROM base AS builder
RUN pip install --no-cache-dir --target=/install -r requirements.txt

FROM base AS linter
COPY --from=builder /install /usr/local/lib/python3.13/site-packages
COPY app.py .
RUN pip install pylint && pylint app.py || exit 0

FROM base AS tester
COPY --from=builder /install /usr/local/lib/python3.9/site-packages
COPY app.py .
RUN pip install pytest && python -m pytest app.py -v || exit 0

FROM python:3.13-alpine AS final
WORKDIR /app
COPY --from=builder /install /usr/local/lib/python3.13/site-packages
COPY app.py .
EXPOSE 5000
CMD ["python", "app.py"]

Mit Buildx kannst du diese effizienter bauen:

docker buildx build --file Dockerfile.optimized -t myapp:optimized --load .

Bild 9 - Mehrstufige Bauwerke

Bild 9 - Mehrstufige Bauwerke

Was ist also das Besondere daran? Buildx verarbeitet unabhängige Phasen parallel. Während der Legacy-Builder die einzelnen Phasen nacheinander ausführen würde, erkennt Buildx, dass die Phasen linter und tester nicht voneinander abhängen und baut sie gleichzeitig auf.

Ein weiterer Vorteil dieser Build-Optimierung ist die Verringerung der Dateigröße. Du kannst die Bildgröße überprüfen, indem du Folgendes ausführst:

docker images myapp

Du siehst dann so etwas wie das hier:

Abbildung 10 - Docker-Abbildgrößen

Abbildung 10 - Docker-Abbildgrößen

Das endgültige Bild in den Alpen ist viel kleiner.

Integration von CI/CD-Pipelines

Auch wenn du lokal arbeitest, kannst du Buildx-Konfigurationen einrichten, die deine CI/CD-Umgebung widerspiegeln.

Erstelle zunächst eine .dockerignore Datei, um die Builds sauber zu halten:

.git
__pycache__
*.pyc
*.pyo
*.pyd
.Python
env
venv
*.so
.coverage
htmlcov

Dann erstellst du ein Build-Skript, das nachahmt, was deine CI-Pipeline tun könnte:

#!/bin/bash
# build.sh - Local CI/CD simulation

echo "Starting CI/CD build process..."

# Setup builder with emulation support
echo "Setting up builder..."
docker buildx create --name cibuilder --use || true
docker buildx inspect --bootstrap

# Run linting
echo "Running lint stage..."
docker buildx build --file Dockerfile.optimized --target linter .

# Run tests
echo "Running test stage..."
docker buildx build --file Dockerfile.optimized --target tester .

# Build for multiple platforms
echo "Building multi-platform image..."
docker buildx build --file Dockerfile.optimized \
  --platform linux/amd64,linux/arm64 \
  --tag myapp:$(date +%Y%m%d) \
  --tag myapp:latest \
  --load \
  --progress=plain \
  .

echo "Build process complete!"

Im Klartext bedeutet das, dass dieses Skript Folgendes tut:

  • Schafft einen eigenen Builder für CI/CD.
  • Führt die Linting-Phase durch.
  • Führt die Testphase durch.
  • Erstellt das endgültige Multiplattform-Bild mit versionierten Tags.

Jetzt kommt der spaßige Teil: Mach das Skript ausführbar und führe es aus:

chmod +x build.sh
./build.sh

Lokale Redaktion

Ein häufiges Problem bei der Arbeit mit Docker ist, dass du jedes Mal, wenn du die Quelldatei änderst, das Image neu erstellen und den Container starten musst. Es braucht einfach zu viel Zeit.

Hier ist die gute Nachricht: Für die lokale Entwicklung mit schnelleren Iterationen kannst du eine Entwicklungsversion erstellen:

# Dockerfile.dev
FROM python:3.13-slim
WORKDIR /app

RUN pip install flask psutil python-dotenv

# Install development tools
RUN pip install pytest pylint watchdog

# Mount app code at runtime instead of copying
CMD ["python", "app.py"]

Führe ihn mit einem Volume Mount aus, um den Code live nachzuladen:

docker buildx build -f Dockerfile.dev -t myapp:dev --load .
docker run -it --rm -p 5000:5000 -v $(pwd):/app myapp:dev

Jetzt kannst du deine app.py Datei lokal bearbeiten, und die Änderungen werden sofort in den laufenden Container übernommen!

Als Nächstes wollen wir über die Leistung sprechen.

Leistungsüberlegungen

Niemand mag einen langsamen Entwicklungsworkflow, und die Parallelisierung mit Docker Buildx kann dabei helfen.

Lass uns herausfinden, wie du deine Builds optimierst und die Leistungsfunktionen von Buildx nutzt, um Bilder schneller zu erstellen.

Parallelisierungstechniken aufbauen

Einer der größten Vorteile von Buildx ist die Möglichkeit, Stufen parallel zu bauen. Der traditionelle Docker-Builder führt jeden Schritt nacheinander aus, aber Buildx analysiert dein Dockerfile und erkennt, welche Schritte gleichzeitig ausgeführt werden können.

Zur Veranschaulichung nehme ich zwei Dateien - Dockerfile.standard und Dockerfile.parallel. Hier sind die Inhalte für beide:

Dockerfile.standard

FROM python:3.13-slim
WORKDIR /app

# System dependencies
RUN apt-get update && apt-get install -y --no-install-recommends \
    gcc \
    g++ \
    && rm -rf /var/lib/apt/lists/*

# Python dependencies
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Application code
COPY app.py .

# Linting
RUN pip install pylint && pylint app.py || true

EXPOSE 5000
CMD ["python", "app.py"]

Dockerfile.parallel

FROM python:3.13-slim AS python-base
WORKDIR /app

# Independent stage for installing system dependencies
FROM python-base AS system-deps
RUN apt-get update && apt-get install -y --no-install-recommends \
    gcc \
    g++ \
    && rm -rf /var/lib/apt/lists/*

# Independent stage for installing Python dependencies
FROM python-base AS python-deps
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Independent stage for static code analysis
FROM python-deps AS linting
COPY app.py .
RUN pip install pylint && pylint app.py || true

# Final stage that combines dependencies
FROM python-base AS final
# Copy from system deps stage
COPY --from=system-deps /usr/bin/gcc /usr/bin/gcc
# Copy from Python deps stage
COPY --from=python-deps /usr/local/lib/python3.13/site-packages /usr/local/lib/python3.13/site-packages
COPY app.py .
EXPOSE 5000
CMD ["python", "app.py"]

Lass uns messen, wie diese parallele Struktur die Bauzeiten verbessert:

# Time the standard sequential build
time docker build -t myapp:standard -f Dockerfile.standard .

# Time the parallel-optimized build with Buildx
time docker buildx build --load -t myapp:parallel -f Dockerfile.parallel .

Zum Vergleich: Der Standard-Build dauerte 18,48 Sekunden, während der parallele Build nur 1,17 Sekunden benötigte!

Für eine noch bessere Leistung kannst du versuchen, die Flags --cache-from und --cache-to zu verwenden, um das lokale Festplatten-Caching zu nutzen:

# First build - create cache
docker buildx build --load -t myapp:latest --cache-to type=local,dest=./buildcache .

# Subsequent builds - use cache
docker buildx build --load -t myapp:latest --cache-from type=local,src=./buildcache .

Du kannst die Größe des Kontexts auch mit sorgfältigen .dockerignore Dateien begrenzen:

# Create a comprehensive .dockerignore
cat > .dockerignore << 'EOF'
.git
.github
.dockerignore
.pytest_cache
__pycache__
*.pyc
*.pyo
*.pyd
.Python
venv
env
node_modules
.coverage
htmlcov
.DS_Store
EOF

Kurz gesagt: Wenn du deine Dockerdateien mit Blick auf die Parallelisierung strukturierst und das fortschrittliche Caching von Buildx nutzt, verbringst du weniger Zeit mit dem Warten auf Builds und mehr Zeit mit der Entwicklung von Funktionen.

Ökosystem-Integration

Docker Buildx existiert nicht in Isolation. Es ist so konzipiert, dass es sich nahtlos in andere Tools in deiner Entwicklungsumgebung integrieren lässt.

Lass uns herausfinden, wie Buildx mit lokalen Entwickler-Tools zusammenarbeitet und deinen Container-Workflow effizienter macht.

Kubernetes-Cluster erstellen

Kubernetes bietet leistungsstarke Funktionen für die Ausführung verteilter Docker Buildx-Operationen in einem Cluster. Wenn du Buildx mit Kubernetes integrierst, kannst du schnellere und stabilere Builds erstellen, die mit den Anforderungen deines Projekts skalieren.

> Bist du neu bei Kubernetes? Die Kubernetes vs. Docker: Unterschiede, die jeder Entwickler kennen sollte post ist dein nächster Halt.

Die Verwendung von Kubernetes für deine Build-Infrastruktur bietet eine Reihe von Vorteilen:

  1. Automatische Skalierung: Kubernetes kann deine Builder Nodes je nach Bedarf hoch- oder runterskalieren und so die Ressourcen in deinem Cluster effizient zuweisen. Du kannst sogar Regeln für die automatische Skalierung basierend auf der CPU-Auslastung einrichten.
  2. Ressourcenoptimierung: Das Kubernetes-Scheduling sorgt dafür, dass deine Builds die benötigten Ressourcen erhalten, ohne dass einzelne Nodes überlastet werden. Du kannst Ressourcenlimits und Anforderungen festlegen, um eine gleichbleibende Leistung zu gewährleisten.
  3. Hohe Verfügbarkeit: Durch die Verteilung von BuildKit-Instanzen auf mehrere Nodes bleibt deine Build-Infrastruktur auch dann verfügbar, wenn einzelne Nodes ausfallen.
  4. Konsistente Umgebungen: Jedes Teammitglied verbindet sich mit der gleichen Build-Infrastruktur, wodurch Probleme wie "funktioniert auf meinem Rechner" vermieden werden.
  5. Parallele Ausführung: Komplexe Builds mit vielen Phasen können parallel auf mehreren Nodes ausgeführt werden, was die Buildzeiten erheblich verkürzt. Ein Projekt, das vor Ort vielleicht 15 Minuten dauert, kann bei der Verteilung in 3-4 Minuten fertig sein.

Betrachte dies als einen eher "theoretischen" Abschnitt, da ein tieferes Eintauchen in Kubernetes ein fortgeschrittenes Thema für sich ist.

Um loszulegen, erstelle eine Datei namens buildkit-deployment.yaml mit folgendem Inhalt:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: buildkit
  namespace: buildkit
spec:
  replicas: 3
  selector:
    matchLabels:
      app: buildkit
  template:
    metadata:
      labels:
        app: buildkit
    spec:
      containers:
      - name: buildkit
        image: moby/buildkit:latest
        args:
        - --addr
        - tcp://0.0.0.0:1234
        ports:
        - containerPort: 1234
        securityContext:
          privileged: true
---
apiVersion: v1
kind: Service
metadata:
  name: buildkit
  namespace: buildkit
spec:
  type: ClusterIP
  ports:
  - port: 1234
    targetPort: 1234
  selector:
    app: buildkit

Der nächste Schritt besteht darin, diese Datei auf deinen Kubernetes-Cluster anzuwenden:

kubectl create namespace buildkit
kubectl apply -f buildkit-deployment.yaml

Verbinde dich schließlich von deinem lokalen Rechner aus mit dieser Bereitstellung:

docker buildx create --name k8s-builder \
  --driver remote \
  --driver-opt endpoint=tcp://<cluster-ip>:1234 \
  --use

Und das war's, du bist startklar!

IDE-Plugin-Unterstützung

IDEs wie Visual Studio Code bieten eine hervorragende Integration mit Docker Buildx durch die Docker-Erweiterung. Diese Integration macht es einfacher, deine Buildx-Workflows direkt von deiner Entwicklungsumgebung aus zu verwalten.

Um mit Docker Buildx in VS Code loszulegen, installiere die "Docker"-Erweiterung aus dem VS Code Marketplace.

Nach der Installation stehen dir mehrere Buildx-spezifische Funktionen zur Verfügung:

  • Wenn du mit der rechten Maustaste auf eine Dockerdatei klickst, erscheint ein Kontextmenü mit der Option "Build Image...", die Buildx unterstützt.
  • Zugriff auf Build-Argumente, Plattformziele und Ausgabeoptionen über die Benutzeroberfläche.
  • Die Möglichkeit, zwischen verschiedenen Builder-Instanzen zu wechseln und diese zu verwalten.
  • Integration mit dem VS Code-Terminal zur Ausführung komplexer Buildx-Befehle.

Abbildung 12 - Docker-Erweiterung für VSCode

Abbildung 11 - Docker-Erweiterung für VSCode

Hier ist ein Beispiel für die Anpassung von VS Code-Aufgaben zur Verwendung von Buildx durch die Erstellung einer .vscode/tasks.json Datei:

{
  "version": "2.0.0",
  "tasks": [
    {
      "label": "Docker: Buildx Build",
      "type": "shell",
      "command": "docker buildx build --load -t ${input:imageName} .",
      "group": {
        "kind": "build",
        "isDefault": true
      }
    },
    {
      "label": "Docker: Buildx Multi-Platform",
      "type": "shell",
      "command": "docker buildx build --platform linux/amd64,linux/arm64 -t ${input:imageName} ."
    }
  ],
  "inputs": [
    {
      "id": "imageName",
      "description": "Image name (with tag):",
      "default": "myapp:latest",
      "type": "promptString"
    }
  ]
}

Mit dieser Konfiguration kannst du schnell auf gängige Buildx-Befehle über das Menü VS Code Tasks(Terminal > Run Task) zugreifen. Die Erweiterung bietet außerdem eine hilfreiche Syntaxhervorhebung für Dockerdateien und eine Autovervollständigung für gängige Docker-Befehle, die deinen Buildx-Workflow noch produktiver machen.

Fehlerbehebung und Fehlersuche

Jedes Entwicklungswerkzeug benötigt manchmal (zu oft) eine Fehlerbehebung, und Docker Buildx ist da keine Ausnahme. In diesem Abschnitt gehe ich mit dir ein paar häufige Probleme durch, damit du sie schnell selbst diagnostizieren kannst und wieder auf den richtigen Weg kommst.

Häufige Probleme und Lösungen

Wenn du mit Buildx arbeitest, stößt du vielleicht auf ein paar gängige Herausforderungen. Hier sind die häufigsten Probleme und ihre Lösungen:

  • Die Erstellung des Builders scheitert. Wenn du beim Erstellen eines Builders mit docker buildx create Fehler siehst, überprüfe deine Docker-Version:
docker version

Buildx erfordert Docker 19.03 oder neuer. Wenn du eine ältere Version verwendest, aktualisiere Docker, um die Buildx-Funktionen nutzen zu können.

Vergewissere dich bei Fehlern wie "kein solches Plugin", dass Buildx richtig installiert ist, indem du es ausführst:

docker buildx version
  • Multiplattform-Build-Fehler. Wenn bei der Erstellung für mehrere Plattformen Fehler wie "exec format error" oder "no matching manifest" auftreten, prüfe, ob QEMU installiert ist:
docker buildx inspect --bootstrap

Falls nötig, installiere Plattform-Emulatoren:

docker run --privileged --rm tonistiigi/binfmt --install all
  • Probleme mit dem Cache. Bei Problemen mit dem Caching kannst du versuchen, deinen lokalen Build-Cache zu löschen:
# Remove specific builder's cache
docker buildx prune -b mybuilder

# Remove all build cache
docker buildx prune --all

> Was genau ist der Docker-Befehl prune? Lerne mit einer Menge praktischer Beispiele.

  • BuildKit Daemon Verbindungsprobleme. Wenn du "fehlgeschlagene Lösung" oder Verbindungsfehler siehst, starte den Builder neu:
docker buildx rm mybuilder
docker buildx create --name mybuilder --use
docker buildx inspect --bootstrap
  • Leistungsbezogene Fragen. Bei langsamen Builds kannst du die Debug-Ausgabe nutzen, um Engpässe zu identifizieren:
docker buildx build --progress=plain --no-cache .

Diese ausführliche Ausgabe hilft dir dabei, herauszufinden, welche Build-Phasen die meiste Zeit in Anspruch nehmen, damit du dein Dockerfile entsprechend optimieren kannst.

  • Der Befehl "Laden" schlägt fehl. Wenn du bei der Verwendung von --load mit Multiplattform-Builds die Meldung "error: docker exporter does not currently support exporting manifest lists" erhältst, denke daran, dass das gleichzeitige Laden mehrerer Plattformen in den Docker-Daemon nicht unterstützt wird. Stattdessen:
# Build for your current platform and load it
docker buildx build --platform linux/amd64 --load -t myapp:latest .
  • Praktiken der Fehlersuche. Bei komplexeren Problemen helfen diese Debugging-Ansätze:
# Enable BuildKit debug logs
BUILDKIT_DEBUG=1 docker buildx build .

# Inspect the builder's internal state
docker buildx inspect

# Check system requirements
docker info

# For specific stage failures, build only up to that stage
docker buildx build --target problem-stage .

# Verify your Docker context
docker context ls

Wenn du diese Schritte zur Fehlerbehebung systematisch durchgehst, kannst du die meisten Buildx-Probleme beheben und einen effizienten Container-Build-Workflow aufrechterhalten.

Zusammenfassung des Docker Buildx Guide

In diesem Docker Buildx-Artikel haben wir eine ganze Menge behandelt! Du hast gesehen, wie dieses leistungsstarke Tool deine Container-Builds schneller und flexibler machen kann.

Erinnere dich an die wichtigsten Vorteile: Du kannst Bilder für mehrere Plattformen mit einem einzigen Befehl erstellen, deine Builds mit fortschrittlichem Caching beschleunigen und deine Bilder mit einer angemessenen Geheimhaltung schützen. Die Leistungsverbesserungen sind real, vor allem wenn du deine Dockerdateien so strukturierst, dass du die Vorteile der parallelen Erstellung nutzen kannst.

Ich benutze sie ständig auf meinem M-Chip Macbook, da nicht alle Bilder für ARM verfügbar sind.

Egal, ob du ein Einzelentwickler oder Teil eines großen Teams bist, Buildx gibt dir Werkzeuge, die zu deinem Arbeitsablauf passen. Du kannst Builds lokal ausführen, sie auf Container verteilen oder sogar auf Kubernetes-Cluster skalieren, wenn dein Bedarf wächst.

Um mehr über Docker und Docker Buildx zu erfahren, empfehle ich dir, die folgenden DataCamp-Kurse zu besuchen:

Docker und Kubernetes beherrschen

Lerne in einem interaktiven Lernpfad die Leistungsfähigkeit von Docker und Kubernetes kennen, um Anwendungen in modernen Umgebungen zu entwickeln und einzusetzen.

Dario Radečić's photo
Author
Dario Radečić
LinkedIn
Senior Data Scientist mit Sitz in Kroatien. Top Tech Writer mit über 700 veröffentlichten Artikeln, die mehr als 10 Millionen Mal aufgerufen wurden. Buchautor von Machine Learning Automation with TPOT.
Themen

Lerne mehr über Docker mit diesen Kursen!

Lernpfad

Containerization and Virtualization with Docker and Kubernetes

13 hr
Learn the power of Docker and Kubernetes, this interactive track will allow you to build and deploy applications in modern environments.
Siehe DetailsRight Arrow
Kurs starten
Mehr anzeigenRight Arrow
Verwandt

Der Blog

Die 50 besten AWS-Interview-Fragen und Antworten für 2025

Ein kompletter Leitfaden zur Erkundung der grundlegenden, mittleren und fortgeschrittenen AWS-Interviewfragen, zusammen mit Fragen, die auf realen Situationen basieren.
Zoumana Keita 's photo

Zoumana Keita

15 Min.

Der Blog

Die 20 besten Snowflake-Interview-Fragen für alle Niveaus

Bist du gerade auf der Suche nach einem Job, der Snowflake nutzt? Bereite dich mit diesen 20 besten Snowflake-Interview-Fragen vor, damit du den Job bekommst!
Nisha Arya Ahmed's photo

Nisha Arya Ahmed

15 Min.

Der Blog

Top 30 Generative KI Interview Fragen und Antworten für 2024

Dieser Blog bietet eine umfassende Sammlung von Fragen und Antworten zu generativen KI-Interviews, die von grundlegenden Konzepten bis hin zu fortgeschrittenen Themen reichen.
Hesam Sheikh Hassani's photo

Hesam Sheikh Hassani

15 Min.

Der Blog

Q2 2023 DataCamp Donates Digest

DataCamp Donates hat im zweiten Quartal 2023 über 20.000 Stipendien an unsere gemeinnützigen Partner vergeben. Erfahre, wie fleißige benachteiligte Lernende diese Chancen in lebensverändernde berufliche Erfolge verwandelt haben.
Nathaniel Taylor-Leach's photo

Nathaniel Taylor-Leach

Der Blog

Lehrer/innen und Schüler/innen erhalten das Premium DataCamp kostenlos für ihre gesamte akademische Laufbahn

Keine Hacks, keine Tricks. Schüler/innen und Lehrer/innen, lest weiter, um zu erfahren, wie ihr die Datenerziehung, die euch zusteht, kostenlos bekommen könnt.
Nathaniel Taylor-Leach's photo

Nathaniel Taylor-Leach

4 Min.

Der Blog

2022-2023 DataCamp Classrooms Jahresbericht

Zu Beginn des neuen Schuljahres ist DataCamp Classrooms motivierter denn je, das Lernen mit Daten zu demokratisieren. In den letzten 12 Monaten sind über 7.650 neue Klassenzimmer hinzugekommen.
Nathaniel Taylor-Leach's photo

Nathaniel Taylor-Leach

8 Min.

Mehr anzeigenMehr anzeigen