Docker auf einem VPS: der Einstieg
Mit Docker betreiben Sie auf einem Server einen Bot, eine Website, eine Datenbank und ein Monitoring, ohne dass sie sich in die Quere kommen, und der Umzug auf einen anderen VPS beschränkt sich auf das Kopieren einiger Dateien und der Daten. Die Installation dauert fünf Minuten, die eigentlichen Probleme kommen später: nach außen offene Datenbank-Ports, Logs mit Dutzenden Gigabyte und Daten, die mit dem Container verschwunden sind. Hier erfahren Sie, wie Sie das von Anfang an vermeiden.
Ein Container ist eine Anwendung samt allen Bibliotheken und Einstellungen, verpackt in ein Image. Auf dem Server startet er mit einem Befehl und läuft auf jedem Linux gleich. Für einen VPS heißt das: Sie müssen keine passenden Versionen von Python, Node.js oder PostgreSQL für das System suchen, mehrere Projekte vertragen sich auf einem Server, und die Datei compose.yaml beschreibt den gesamten Satz an Diensten so, dass Sie ihn auf einem neuen Server in Minuten hochfahren.
Welchen VPS Docker braucht
Virtualisierung: KVM. Docker nutzt Funktionen des Linux-Kernels: Namespaces, cgroups, eigene Netzwerkregeln. Unter KVM hat der Server einen eigenen Kernel, und Docker läuft ohne Einschränkungen. Unter OpenVZ und LXC teilt sich der Server den Kernel mit anderen Kunden, und Docker startet dort entweder gar nicht oder läuft mit Einschränkungen, die vom Hoster abhängen. Mehr dazu im Artikel KVM oder OpenVZ: was Sie wählen sollten.
Arbeitsspeicher und Kerne. Docker selbst braucht wenig, den Speicher verbrauchen die Container. Richtwerte:
- 1 GB – ein bis zwei leichte Container: Bot, kleine API, Monitoring;
- 2 Kerne und 2 GB – Website mit Datenbank und Reverse Proxy, einige kleine Dienste;
- 2–4 Kerne und 4 GB – mehrere Projekte, PostgreSQL, Redis, Image-Builds direkt auf dem Server;
- ab 8 GB – GitLab, n8n mit vielen Workflows, Elasticsearch und andere schwere Dienste.
Festplatte. Images brauchen Platz: Ein Basis-Image mit Python oder Node.js wiegt Hunderte Megabyte, und alte Versionen sammeln sich bei jedem Update an. Nehmen Sie ab 30 GB auf NVMe, für Image-Builds auf dem Server mehr.
Laut accsly-Katalog vom 1. November 2026 kostet ein KVM-Tarif mit 2 Kernen und 2 GB Arbeitsspeicher im Marktmedian etwa 13,50 € im Monat, ein Viertel dieser Tarife liegt unter etwa 8 €. Mit 2 Kernen und 4 GB sind es etwa 18 €, ein Viertel unter etwa 11 € (aus Rubel umgerechnet und gerundet). Auswahlen: VPS für Docker, VPS mit KVM, VPS mit 4 GB. Zum Ausprobieren ist die stundenweise Abrechnung praktisch: Ein Server für einen Abend kostet weniger als einen Euro.
Vor der Installation
Nehmen Sie ein frisches Ubuntu 22.04 oder 24.04 LTS oder Debian 12 und richten Sie zuerst den Grundschutz ein: Updates, Anmeldung per Schlüssel, eigener Benutzer, Firewall. All das finden Sie im Artikel Die ersten 10 Schritte nach dem VPS-Kauf: Sicherheit. Ein Control Panel für Websites brauchen Sie auf einem Server mit Containern meist nicht, warum, steht im Artikel Server-Control-Panels.
Installation aus dem offiziellen Repository
Das Paket docker.io aus dem Ubuntu-Repository hinkt der aktuellen Version oft hinterher und enthält nicht immer Compose. Zuverlässiger ist die Installation aus dem Docker-Repository. Die Befehle für Ubuntu laut offizieller Dokumentation:
sudo apt update
sudo apt install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc
sudo tee /etc/apt/sources.list.d/docker.sources <<EOF
Types: deb
URIs: https://download.docker.com/linux/ubuntu
Suites: $(. /etc/os-release && echo "${UBUNTU_CODENAME:-$VERSION_CODENAME}")
Components: stable
Architectures: $(dpkg --print-architecture)
Signed-By: /etc/apt/keyrings/docker.asc
EOF
sudo apt update
sudo apt install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
Für Debian sind die Befehle dieselben, nur wird in den Adressen linux/ubuntu durch linux/debian ersetzt, und statt UBUNTU_CODENAME wird VERSION_CODENAME verwendet. Prüfen Sie die Installation:
sudo docker run hello-world
docker compose version
Es gibt auch einen Installer mit einem Befehl über get.docker.com, doch die Docker-Dokumentation selbst rät davon für Produktivserver ab: Er installiert viele Pakete ohne Rückfrage und nimmt immer die neueste Version.
Die Gruppe docker. Damit Sie nicht vor jeden Befehl sudo schreiben müssen, fügen Sie den Benutzer der Gruppe docker hinzu: sudo usermod -aG docker $USER und neu anmelden. Denken Sie daran, dass das root-Rechten entspricht: Ein Mitglied der Gruppe kann einen Container mit Zugriff auf das gesamte Dateisystem des Servers starten. Nehmen Sie dort nur Ihr eigenes Arbeitskonto auf.
Das erste Projekt mit Docker Compose
Einzelne docker run-Befehle mit einem Dutzend Parametern vergisst man schnell. Bequemer ist es, das Projekt in einer Datei compose.yaml in einem eigenen Ordner zu beschreiben, etwa /opt/app. Ein Beispiel: eine Webanwendung mit PostgreSQL-Datenbank:
services:
app:
image: ghcr.io/example/app:1.4.2
restart: unless-stopped
environment:
DATABASE_URL: postgres://app:${DB_PASSWORD}@db:5432/app
ports:
- "127.0.0.1:8080:8080"
depends_on:
- db
db:
image: postgres:16
restart: unless-stopped
environment:
POSTGRES_USER: app
POSTGRES_PASSWORD: ${DB_PASSWORD}
volumes:
- db-data:/var/lib/postgresql/data
volumes:
db-data:
Legen Sie das Passwort daneben in eine Datei .env mit der Zeile DB_PASSWORD=... und schützen Sie sie vor dem Lesen durch andere Benutzer: chmod 600 .env. Start mit docker compose up -d, Log mit docker compose logs -f app, Stopp mit docker compose down.
Drei Dinge sind in diesem Beispiel wichtig:
restart: unless-stopped– die Container starten nach einem Neustart des Servers wieder;- die Datenbank hat keinen Abschnitt
ports: Die Anwendung erreicht sie unter dem Namendbim internen Netz des Projekts, von außen ist sie nicht erreichbar; - der Port der Anwendung ist nur auf
127.0.0.1veröffentlicht, nach außen stellt ihn nginx oder Caddy mit TLS-Zertifikat bereit.
Ports und Firewall
Die größte Falle für Einsteiger. Veröffentlicht ein Container einen Port als "5432:5432", legt Docker selbst iptables-Regeln an, und dieser Port wird unabhängig von den Regeln von ufw oder firewalld nach außen geöffnet. Die Docker-Dokumentation warnt ausdrücklich: Veröffentlichte Container-Ports gelten unabhängig von den Firewall-Regeln. Genau so landen PostgreSQL-, MongoDB- und Redis-Datenbanken ohne Passwort am häufigsten im Internet.
Die Regel ist einfach: Veröffentlichen Sie nach außen nur, was für alle erreichbar sein soll – meist die Ports 80 und 443 des Reverse Proxys. Alles andere entweder ohne Abschnitt ports oder gebunden an 127.0.0.1. Was der Server tatsächlich abhört, zeigt der Befehl ss -tlnp, von außen prüfen Sie es von einem anderen Rechner mit nc -zv IP-des-Servers 5432.
Logs und Speicherplatz
Standardmäßig schreibt Docker die Ausgabe der Container ohne Größenbegrenzung in JSON-Dateien. Eine gesprächige Anwendung füllt die Festplatte in ein paar Monaten, und der Server steht. Begrenzen Sie die Logs für alle Container in der Datei /etc/docker/daemon.json:
{
"log-driver": "json-file",
"log-opts": {
"max-size": "10m",
"max-file": "3"
}
}
Danach sudo systemctl restart docker. Die Einstellung gilt für Container, die danach erstellt werden, legen Sie die Projekte deshalb neu an: docker compose up -d --force-recreate.
Der zweite Platzfresser sind alte Images. Wie viel belegt ist, zeigt docker system df, ungenutzte Images löschen Sie mit docker image prune -a. Den Befehl docker system prune --volumes sollten Sie nicht ausführen, ohne genau zu wissen, was er tut: Er löscht auch die Volumes gestoppter Projekte samt Daten.
Wo die Daten liegen und wie Sie sie sichern
Alles, was eine Anwendung innerhalb des Containers geschrieben hat, verschwindet, wenn der Container neu erstellt wird. Erhalten bleibt nur, was in Volumes (volumes) oder in eingebundenen Ordnern des Servers liegt. Prüfen Sie vor dem Start eines Images in seiner Dokumentation, welche Ordner in ein Volume gehören: bei PostgreSQL /var/lib/postgresql/data, bei anderen Anwendungen eigene Pfade.
Datenbankdateien im laufenden Betrieb zu kopieren ist unzuverlässig. Erstellen Sie einen Dump über den Container selbst:
docker compose exec -T db pg_dump -U app app | gzip > /backup/app-$(date +%F).sql.gz
Tragen Sie diesen Befehl in cron ein und schicken Sie die Kopien zusammen mit compose.yaml und .env nach außerhalb des Servers. Wie Sie externe Speicherung und Prüfung der Kopien einrichten, steht im Artikel VPS-Backups: Strategien und Werkzeuge.
Container aktualisieren
Geben Sie in compose.yaml eine konkrete Image-Version an (postgres:16, app:1.4.2), nicht latest: Dann kommt ein Update, wenn Sie es geplant haben, und nicht bei einem zufälligen Neustart. Ablauf eines Updates:
- einen Dump der Datenbank erstellen;
- die Version in
compose.yamländern; docker compose pullunddocker compose up -d;- Log und Funktion der Anwendung prüfen, danach das alte Image löschen.
Major-Versionen von Datenbanken, etwa PostgreSQL 16 → 17, lassen sich so nicht aktualisieren: Die neue Version braucht eine Datenübernahme per Dump und Import. Das System des Servers und Docker selbst aktualisieren Sie mit dem üblichen apt upgrade.
Wie es weitergeht
Laufen mehrere Projekte auf dem Server, lohnen sich ein Reverse Proxy, der selbst Zertifikate bezieht, und ein Verfügbarkeitsmonitoring. Für einen Bot in Python oder Node.js im Container reicht ein kleiner Server, Details im Artikel VPS für einen Telegram-Bot. Werden es viele Container und reicht ein Server nicht mehr, ist der nächste Schritt ein Verbund mehrerer Server unter einem Orchestrator, Tarife in der Auswahl VPS für Kubernetes. Für Automatisierung und CI in Containern gibt es die Auswahlen VPS für n8n und VPS für GitLab.