← Blog

Metabase mit Postgres selbst hosten

Railyard

21. Juni 2026 · 6 Min. Lesezeit

Folge dem auf deinem eigenen Server. Kostenlos starten, keine Karte nötig

Die meisten BI-Tools verlangen pro Sitzplatz, was aus “das ganze Team soll das Dashboard sehen” einen Posten macht, der jedes Mal wächst, wenn jemand Neues Zugriff braucht. Metabase ist Open-Source-Self-Service-Analyse, die genau das erledigt, was wichtig ist: eine Datenbank verbinden, Diagramme und Dashboards bauen, nicht-technischen Leuten erlauben, Fragen zu stellen, ohne SQL zu schreiben, ohne Rechnung pro Sitzplatz, sobald es auf deinem eigenen Server läuft. Diese Anleitung richtet es mit einer eigenen Postgres-Datenbank zum Speichern von Dashboards und Fragen ein, hinter Caddy für HTTPS, und zeigt dann den Ein-Klick-Weg.

Am Ende läuft Metabase auf deiner eigenen Domain, verbunden mit seinem eigenen Metadaten-Speicher, bereit, auf die Datenbank oder das Warehouse zu zeigen, das du tatsächlich analysieren willst.

Was du brauchst

  • Einen Server. Metabase selbst ist eine JVM-Anwendung mit bescheidenen Anforderungen für ein kleines Team; ein Hetzner CX23 (2 vCPU, 4 GB RAM, 40 GB NVMe) für 5,99 €/Monat exkl. MwSt. betreibt Metabase und sein eigenes Postgres bequem. Stärkere Dashboard-Nutzung oder große Ergebnismengen wollen mehr Arbeitsspeicher; ein CX33 (4 vCPU, 8 GB, 8,99 €/Monat) ist die nächste Stufe.
  • Eine Domain oder Subdomain mit einem DNS-A-Eintrag, der auf den Server zeigt (diese Anleitung nutzt bi.beispiel.com).
  • SSH-Zugriff und etwa 15 Minuten.
  • Optional die Datenbank oder das Warehouse, das Metabase tatsächlich abfragen soll. Diese Anleitung richtet nur Metabases eigene Anwendungsdatenbank ein; deine echte Datenquelle verbindest du erst nach dem ersten Login in der App.

Schritt 1: Server bereitstellen und DNS darauf zeigen lassen

bi.beispiel.com.  A  203.0.113.40
ssh root@203.0.113.40
apt update && apt upgrade -y

Schritt 2: Docker installieren

curl -fsSL https://get.docker.com | sh
systemctl enable --now docker
docker --version
docker compose version

Schritt 3: Umgebungsdatei schreiben

mkdir -p /opt/metabase && cd /opt/metabase
DB_NAME=metabase
DB_USER=metabase
DB_PASSWORD=aendere-dies-in-eine-zufaellige-zeichenfolge

Dieses Passwort ist für Metabases eigene Postgres-Datenbank, die Dashboards, gespeicherte Fragen und Benutzerkonten enthält, nicht für die Datenquelle, die du später anbindest.

Schritt 4: Docker-Compose-Datei schreiben

Diese Anleitung nutzt das aktuelle stabile Release, Metabase v0.64.3.4, ausdrücklich festgepinnt statt latest, damit ein unabhängiges Upstream-Release deinen Stack nicht unter dir verändern kann:

services:
  caddy:
    image: caddy:2
    restart: unless-stopped
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile
      - caddy-data:/data
      - caddy-config:/config

  metabase:
    image: metabase/metabase:v0.64.3.4
    restart: unless-stopped
    environment:
      MB_DB_TYPE: postgres
      MB_DB_HOST: db
      MB_DB_PORT: "5432"
      MB_DB_DBNAME: ${DB_NAME}
      MB_DB_USER: ${DB_USER}
      MB_DB_PASS: ${DB_PASSWORD}
    depends_on:
      db:
        condition: service_healthy
    healthcheck:
      test: ["CMD-SHELL", "curl -f http://localhost:3000/api/health || exit 1"]
      interval: 10s
      timeout: 5s
      retries: 10

  db:
    image: postgres:18-alpine
    restart: unless-stopped
    environment:
      POSTGRES_DB: ${DB_NAME}
      POSTGRES_USER: ${DB_USER}
      POSTGRES_PASSWORD: ${DB_PASSWORD}
    volumes:
      - metabase-db-data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U ${DB_USER} -d ${DB_NAME}"]
      interval: 5s
      timeout: 5s
      retries: 5

volumes:
  metabase-db-data:
  caddy-data:
  caddy-config:

MB_DB_TYPE, MB_DB_HOST, MB_DB_PORT, MB_DB_DBNAME, MB_DB_USER und MB_DB_PASS sind genau die Umgebungsvariablen, die Metabases eigene Dokumentation vorgibt, um es auf eine externe Postgres-Datenbank zu zeigen, statt auf die eingebettete H2-Datenbank, auf die es ohne sie zurückfällt und die nicht für mehr als einen schnellen Test gedacht ist. Prüfe die Datei:

docker compose config

Schritt 5: Caddyfile schreiben

bi.beispiel.com {
    reverse_proxy metabase:3000
}

Schritt 6: Stack hochfahren

docker compose up -d
docker compose ps

Du solltest caddy, metabase und db alle als running sehen, wobei metabase als healthy meldet, sobald sein eigener Start abgeschlossen ist, was beim ersten Boot ein bis zwei Minuten dauert, da es sein Metadaten-Schema in Postgres initialisiert. Verfolge die Logs, falls es länger dauert:

docker compose logs -f metabase

Besuche https://bi.beispiel.com; du solltest auf Metabases Ersteinrichtungs-Assistenten über ein gültiges HTTPS-Zertifikat landen.

Schritt 7: Einrichtung abschließen und eine echte Datenquelle verbinden

Der Einrichtungsassistent legt dein Admin-Konto direkt an, kein Standardpasswort, das du nachträglich ändern müsstest, wie es bei manchen selbst gehosteten Apps üblich ist. Sobald du drin bist, füge die Datenbank, die du wirklich analysieren willst, unter Settings → Admin settings → Databases → Add a database hinzu. Das ist eine separate Verbindung zum Postgres-Container aus Schritt 4, der nur Metabases eigene Fragen und Dashboards speichert, nicht deine Daten.

Schritt 8: Metadatenbank sichern

Dashboards, gespeicherte Fragen und Benutzerkonten liegen im Postgres-Container aus Schritt 4, nicht in den Datenquellen, die du verbindest. Sichere ihn regelmäßig:

docker compose exec -T db pg_dump -U ${DB_USER} ${DB_NAME} | gzip > /opt/metabase/backups/metabase-$(date +%F).sql.gz

Kopiere die Datei per Cronjob vom Server. Sie wiederherzustellen nach einer Neuinstallation bringt deine Dashboards und Fragen zurück; deine tatsächlichen Datenquellen sind davon in jedem Fall nicht betroffen, da sie hier nicht gespeichert sind.

Schritt 9: Upgrades

docker compose pull metabase
docker compose up -d metabase

Prüfe Metabases eigene Release-Notes, bevor du über eine Hauptversion hinweg springst; es führt seine eigenen Datenbankmigrationen automatisch beim Start aus, und ein Backup aus Schritt 8 vorher ist eine billige Versicherung gegen einen Fehlschlag.

Die Abkürzung: mit Railyard

Alles oben Beschriebene, die beiden Container, die Umgebungsdatei, der Reverse Proxy, ist das, was Railyards Metabase + Postgres-Stack-Template für dich einrichtet. Wähle es aus dem Template-Katalog: https://app.railyard.run/deploy?stack=metabase-postgres. Railyard stellt Metabase und eine eigene Postgres-Instanz zusammen bereit und verdrahtet die Verbindung automatisch, es gibt also nichts händisch zu verbinden. Die gleiche Trennung aus Schritt 7 gilt weiterhin: Diese Postgres-Instanz ist Metabases eigener Metadaten-Speicher, und dein tatsächliches Warehouse oder deine Produktionsdatenbank wird separat unter Settings → Databases nach dem ersten Login verbunden. Von dort aus laufen Datenbank-Backups nach Plan und lassen sich mit einem Klick wiederherstellen.

Troubleshooting

HTTPS wird nie ausgestellt. DNS zeigt noch nicht auf den Server. dig +short bi.beispiel.com sollte die IP des Servers zurückgeben.

Der Metabase-Container startet direkt nach dem Start in einer Schleife neu. Prüfe zuerst docker compose logs metabase auf einen Datenbankverbindungsfehler; die häufigste Ursache ist, dass MB_DB_PASS nicht mit dem übereinstimmt, was tatsächlich in der Umgebung des db-Containers steht, meist weil .env beim ersten Hochfahren des Stacks nicht vorhanden war oder falsch benannt wurde.

Der erste Login dauert lange oder läuft im Browser in einen Timeout. Metabase führt beim ersten Boot seine eigenen Schema-Migrationen gegen Postgres aus, was je nach Servergeschwindigkeit ein bis zwei Minuten dauern kann. Prüfe, ob docker compose logs metabase noch Fortschritte zeigt, bevor du annimmst, dass etwas kaputt ist.

Dashboards laden langsam. Das liegt häufiger an der Datenquelle, die Metabase abfragt, als an Metabase selbst; große unindizierte Abfragen gegen eine Produktionsdatenbank sind langsam, egal wer fragt. Prüfe die Abfrageleistung gegen die tatsächlich verbundene Datenbank und erwäge eine Read-Replica für starke Reporting-Last, falls die Produktionsdatenbank selbst unter Druck steht.

Speichermangel auf einem kleinen Server. Die JVM, auf der Metabase läuft, hat echte Mindestanforderungen an Arbeitsspeicher; ein CX23 reicht für ein kleines Team, aber wenn du auf derselben Box noch andere Container betreibst, zeigt docker compose ps dann metabase als exited, und dmesg | grep -i "out of memory" bestätigt das; die Lösung ist mehr Speicher oder weniger Dinge, die sich diesen Server teilen.

FAQ

Kann ich mehr als eine Datenbank verbinden? Ja, beliebig viele, jeweils separat konfiguriert unter Settings → Databases; Metabase selbst braucht für seine eigene Speicherung nur die eine Postgres-Instanz aus dieser Anleitung, egal wie viele Quellen du sonst anbindest.

Braucht Metabase Internetzugang, um zu laufen? Nein, einmal installiert läuft es vollständig gegen seine eigene Postgres-Datenbank und die verbundenen Datenquellen, ohne ausgehende Abhängigkeit für den Tagesbetrieb.

Was ist der Unterschied zwischen der Open-Source- und der bezahlten Version? Die Open-Source-Edition deckt Dashboards, Fragen, Alerts und den Query-Builder ab, die diese Anleitung einrichtet; Metabases bezahlte Stufen fügen Dinge wie SSO, Audit-Logs und White-Labeling für größere Organisationen hinzu, die diese Anleitung nicht braucht.

Können nicht-technische Leute das wirklich nutzen, ohne SQL zu lernen? Das ist genau das Feature, um das Metabase herum gebaut ist: Sein Fragen-Builder lässt jemanden Daten über eine visuelle Oberfläche filtern, gruppieren und als Diagramm darstellen, mit SQL als Option für alle, die es wollen, nicht als Pflicht.

Wie ist das günstiger als ein gehostetes BI-Tool? Die Kosten eines gehosteten Tools pro Sitzplatz wachsen mit der Anzahl der Leute im Unternehmen, die ein Dashboard brauchen; ein CX23 für rund sechs Euro im Monat kostet gleich viel, ob drei oder dreißig Leute darauf schauen.

Kann ich Metabase ohne Docker betreiben? Ja, es gibt es auch als einfache JAR-Datei, die du direkt mit einer JVM ausführst, was manche Teams bevorzugen, die auf einem Server bereits Java-Deployments verwalten; das Docker-Image ist der Weg, den diese Anleitung und Railyards Template beide nutzen, da es die JVM-Version und Abhängigkeiten zusammen mit der App festpinnt, statt sich auf das zu verlassen, was auf dem Host schon installiert ist.

Metabase gibt einem Team Self-Service-Dashboards, ohne dass “eine Person mehr braucht Zugriff” zu einem Abrechnungsthema wird. Das Setup hier sind zwei Container, eine Umgebungsdatei und ein Reverse Proxy; von dort aus sind es dieselben Fragen-Builder und Dashboards, nur auf einem Server mit festen monatlichen Kosten statt mit der Mitarbeiterzahl mitwachsenden Kosten.

Warum Leute sich dafür Railyard entscheiden

  • Dein eigenes Cloud-Konto. Deploye auf DigitalOcean, Hetzner, Vultr, AWS, OVHcloud oder jedem Linux-Server per SSH, direkt von deinem Anbieter abgerechnet, ohne Aufschlag.
  • Ein fester Preis pro Team. Free ist für immer kostenlos: ein Server plus ein Datenbankserver, drei Apps, keine Karte. Pro kostet 19 $ im Monat für bis zu fünf Server und unbegrenzte Apps. Team kostet 49 $ im Monat mit unbegrenzten Servern. Keine Kosten pro App, pro Deployment, pro Sitz oder pro Gigabyte.
  • Templates mit einem Klick. Deploye Open-Source-Apps, wie Datenbanken, Analytics und Dev-Tools, mit einem Klick auf deinem eigenen Server.
  • Verwaltete Datenbanken. Postgres, MySQL und Redis mit geplanten, wiederherstellungsgeprüften Backups und Point-in-Time-Recovery.
  • Push-to-Deploy. Deploye von GitHub, GitLab oder der CLI, mit automatischem HTTPS und Releases ohne Ausfallzeit.

Server-Setup überspringen

Deploye Metabase mit bereits fertig eingerichtetem Postgres aus Railyards Template-Katalog.

Kostenloser Plan, keine Kreditkarte, und 14 Tage Pro für jedes neue Team. Ein fester Preis pro Team.