Weniger Tools, mehr Postgres – Ein Survival-Guide für dein Backend
Wie PostgreSQL-Extensions dein Backend vereinfachen und bis zu 10 Services ersetzen können
Einleitung
Moderne Web-Stacks wirken oft wie ein überfüllter Werkzeugkasten: Redis hier, Elasticsearch dort, Auth0 für Logins, Firebase für Realtime, Cronjobs über Lambda, Analytics via SaaS.
Das Ergebnis: Komplexität, Kosten und viele Bruchstellen.
Die gute Nachricht: Postgres 2025 kann die meisten dieser Aufgaben selbst übernehmen.
Wie wir bereits in unseren Artikeln zu PostgreSQL als Plattform und PostgreSQL in der Praxis gezeigt haben, kann PostgreSQL mit den richtigen Extensions locker fünf bis zehn Services ersetzen – ohne dein Backend in eine Service-Wüste zu zerlegen.
Was Postgres ersetzt (Überblick)
| Klassisches Tool | Postgres-Feature | Geeignet für |
|---|---|---|
| Redis | Unlogged Tables (Cache) | Sessions, Tokens |
| Elasticsearch | TSVECTOR (Volltextsuche) | Blogs, Foren, Help-Center |
| MongoDB | JSONB (flexible Dokumente) | User-Settings, Logs |
| RabbitMQ / Cronjobs | pg_cron + Outbox-Pattern | Jobs, Event-Trigger |
| Pinecone | pgvector (AI-Suche) | RAG, Empfehlungen |
| Firebase / Auth0 | pgcrypto + Row-Level Security | Login, Multi-Tenant-SaaS |
| Google Analytics | Events + SQL Queries | Klick-Tracking, Funnel |
| Mixpanel | TimescaleDB / pgme | Retention, Dashboards |
Praxis-Snippets – so ersetzt du einzelne Tools
Jobs & Zeitpläne mit pg_cron
SELECT cron.schedule(
'clean_sessions',
'0 * * * *',
$$ DELETE FROM sessions WHERE expires_at < now(); $$
);
Ersetzt: Externe Cronjobs oder Functions für einfache Maintenance-Tasks.
Cache mit UNLOGGED TABLES
CREATE UNLOGGED TABLE session_cache (
token UUID PRIMARY KEY,
user_id INT,
expires_at TIMESTAMPTZ
);
Ersetzt: Redis für schnelle, flüchtige Daten.
AI-Suche mit pgvector
SELECT content
FROM docs
ORDER BY embedding <-> '[0.011, -0.043, ...]'::vector
LIMIT 5;
Ersetzt: Pinecone & Co. für kleine bis mittlere Embedding-Szenarien.
Auth & Zugriff mit pgcrypto + RLS
UPDATE users
SET password = crypt('pw', gen_salt('bf'));
ALTER TABLE todos ENABLE ROW LEVEL SECURITY;
CREATE POLICY user_owns_todo ON todos
USING (user_id = current_setting('app.current_user')::INT);
Ersetzt: Login-Logik & Tenant-Isolation direkt in der DB.
Volltextsuche mit TSVECTOR
UPDATE articles
SET search = to_tsvector('english', title || ' ' || body);
SELECT title
FROM articles
WHERE search @@ plainto_tsquery('postgres vector magic')
ORDER BY ts_rank(search, plainto_tsquery('postgres vector magic')) DESC;
Ersetzt: Eine eigene Elasticsearch-Instanz.
Analytics selbst gebaut
CREATE TABLE pageviews (
path TEXT,
user_id INT,
viewed_at TIMESTAMPTZ DEFAULT now()
);
SELECT path, COUNT(*)
FROM pageviews
GROUP BY path
ORDER BY count DESC;
Ersetzt: Google Analytics/Mixpanel – und du behältst die Datenhoheit.
Erweiterungen für mehr Praxisnutzen
Before/After-Szenario
Vorher (klassischer Stack für eine kleine App):
- Redis für Sessions
- Auth0 für Logins
- Firebase für Realtime
- Elasticsearch für Suche
- Lambda-Cronjobs für Cleanup
- Mixpanel für Analytics
Nachher (gleiche App nur mit Postgres):
- Sessions → Unlogged Tables
- Auth → pgcrypto + RLS
- Realtime → LISTEN/NOTIFY oder ElectricSQL
- Suche → TSVECTOR
- Cronjobs → pg_cron
- Analytics → Events-Tabellen + SQL
Ergebnis: Ein einziger Postgres-Cluster, einheitliches Monitoring, weniger Rechnungen.
Kosten-Vergleich (vereinfacht)
Klassischer Multi-Service-Stack:
- Redis: 10$/Monat
- Elasticsearch: 50$/Monat
- Auth0: 50$/Monat
- Firebase: 25$/Monat
- Mixpanel: 25$/Monat
- Gesamt: 160$/Monat für Basis-Funktionen
Postgres-DBaaS Alternative:
- Supabase / Neon / DO Managed Postgres: 25–50$/Monat inkl. aller Features
Einsparung: Vor allem für Indie-Entwickler & KMU ein entscheidender Unterschied von 110+ $/Monat.
DevOps-Perspektive
Früher: 6 Services deployen, überwachen, updaten. Heute: Eine Postgres-Instanz, zentral Logs, Metriken, Backups.
Tools wie pg_stat_statements oder pg_cron-Views liefern Einblicke direkt aus der Datenbank.
Erweiterte Auth
Zusätzlich zu RLS und pgcrypto:
pgjwt: JWT-Handling direkt in SQL. Use Case: API-Token ausgeben, validieren, sogar Ablaufzeiten in SQL prüfen.
SELECT sign(
row_to_json(r),
'your-secret-key'
) AS token
FROM (
SELECT 'user123' AS sub,
extract(epoch from now())::integer + 3600 AS exp
) r;
Kombinierte Features
- FTS + pgvector: Semantische Suche + klassische Volltext-Rankings
- JSONB + RLS: Multi-Tenant SaaS – flexible Daten je Kunde, aber streng isoliert
Tools im Postgres-Ökosystem
- ElectricSQL: Echtzeit-Sync zwischen Client und Server
- PostGraphile: GraphQL-API direkt aus DB-Schema
- pgme: Analytics & Dashboards einfach in Postgres
Roadmap-Hinweis
Mit Postgres 18 kommen u. a. mehr SQL/JSON-Funktionen und bessere Parallelisierung.
Bedeutung: Die Plattform wird noch stärker, weniger externe Tools werden nötig.
Storytelling-Beispiel: Von der Service-Hölle zur Postgres-Simplicity
Der Ausgangspunkt (2019):
Alex, ein Indie-Entwickler, startet sein SaaS-Projekt “TaskFlow” – eine Projektmanagement-App für kleine Teams. Wie viele andere folgt er den damaligen Best Practices und baut einen “modernen” Stack:
- MongoDB für flexible User-Daten und Projektstrukturen
- Redis für Session-Management und Caching
- Elasticsearch für die Projektsuche
- Auth0 für Benutzerverwaltung und SSO
- Firebase für Realtime-Updates zwischen Teammitgliedern
- Mixpanel für User-Analytics und Conversion-Tracking
- AWS Lambda für Cronjobs (E-Mail-Versand, Cleanup-Tasks)
Die schmerzhaften Realitäten:
Komplexität explodiert:
- 7 verschiedene Dashboards zu überwachen
- Jeder Service hat eigene Logs, Metriken, Alerts
- Deployment bedeutet: 7 Services koordinieren
Kosten steigen unkontrolliert:
- MongoDB Atlas: 45$/Monat
- Redis Cloud: 15$/Monat
- Elasticsearch Service: 65$/Monat
- Auth0: 70$/Monat (wegen SSO-Features)
- Firebase: 35$/Monat
- Mixpanel: 25$/Monat
- AWS Lambda + CloudWatch: 20$/Monat
- Gesamt: 275$/Monat – und das bei nur 500 aktiven Nutzern
Ausfälle werden zum Alptraum:
- Redis fällt aus → alle Sessions weg
- Elasticsearch überlastet → Suche funktioniert nicht
- Auth0 hat Maintenance → niemand kann sich einloggen
- Jeder Service kann das ganze System lahmlegen
Die Postgres-Transformation (2025):
Nach 6 Jahren Schmerzen entscheidet Alex: Alles muss weg, alles wird Postgres.
Migration Schritt für Schritt:
1. MongoDB → PostgreSQL JSONB
-- Vorher: Komplexe MongoDB-Queries
-- Nachher: SQL mit JSON-Power
CREATE TABLE projects (
id SERIAL PRIMARY KEY,
name TEXT,
settings JSONB,
members JSONB,
created_at TIMESTAMPTZ DEFAULT now()
);
-- Flexible Queries wie in MongoDB, aber mit SQL
SELECT name
FROM projects
WHERE settings->>'priority' = 'high'
AND members @> '[{"role": "admin"}]';
2. Redis → UNLOGGED TABLES
CREATE UNLOGGED TABLE sessions (
token UUID PRIMARY KEY,
user_id INTEGER,
data JSONB,
expires_at TIMESTAMPTZ
);
-- Auto-Cleanup via pg_cron
SELECT cron.schedule('cleanup-sessions', '*/5 * * * *',
'DELETE FROM sessions WHERE expires_at < now()');
3. Elasticsearch → TSVECTOR
-- Projektsuche ohne externe Engine
ALTER TABLE projects ADD COLUMN search_vector tsvector;
UPDATE projects
SET search_vector = to_tsvector('english', name || ' ' || description);
-- Suche mit Ranking
SELECT name, ts_rank(search_vector, query) as rank
FROM projects, plainto_tsquery('team collaboration') query
WHERE search_vector @@ query
ORDER BY rank DESC;
4. Auth0 → pgcrypto + RLS
-- Passwort-Hashing
CREATE OR REPLACE FUNCTION hash_password(password TEXT)
RETURNS TEXT AS $$
BEGIN
RETURN crypt(password, gen_salt('bf', 10));
END;
$$ LANGUAGE plpgsql;
-- Multi-Tenant Isolation
ALTER TABLE projects ENABLE ROW LEVEL SECURITY;
CREATE POLICY tenant_isolation ON projects
USING (tenant_id = current_setting('app.current_tenant')::integer);
5. Firebase Realtime → LISTEN/NOTIFY
-- Real-time Updates ohne externe API
CREATE OR REPLACE FUNCTION notify_project_update()
RETURNS TRIGGER AS $$
BEGIN
PERFORM pg_notify('project_updates',
json_build_object('project_id', NEW.id, 'action', TG_OP)::text);
RETURN NEW;
END;
$$ LANGUAGE plpgsql;
CREATE TRIGGER project_update_trigger
AFTER INSERT OR UPDATE OR DELETE ON projects
FOR EACH ROW EXECUTE FUNCTION notify_project_update();
6. Mixpanel → Event-Tables
CREATE TABLE events (
id BIGSERIAL PRIMARY KEY,
user_id INTEGER,
event_type TEXT,
properties JSONB,
timestamp TIMESTAMPTZ DEFAULT now()
);
-- Analytics ohne externe Tools
SELECT
date_trunc('day', timestamp) as day,
COUNT(*) as daily_active_users
FROM events
WHERE event_type = 'login'
AND timestamp > now() - interval '30 days'
GROUP BY day
ORDER BY day;
Die Ergebnisse nach der Migration:
Drastische Kostensenkung:
- Vorher: 275$/Monat für 7 Services
- Nachher: 35$/Monat für Neon Postgres Pro
- Einsparung: 240$/Monat = 2.880$/Jahr
Ops-Aufwand reduziert um 80%:
- Vorher: 7 Dashboards, 7 Alert-Systeme, 7 Update-Zyklen
- Nachher: 1 Postgres-Dashboard, pg_stat_statements, einheitliche Logs
Performance verbessert:
- Vorher: Netzwerk-Latenz zwischen 7 Services
- Nachher: Alles in einer DB, optimierte Joins statt API-Calls
- Suchgeschwindigkeit: 40% schneller durch TSVECTOR vs. Elasticsearch
Reliability erhöht:
- Vorher: 7 Single Points of Failure
- Nachher: 1 hochverfügbare Postgres-Instanz mit Replikation
- Uptime: Von 99.5% auf 99.9% gestiegen
Development-Geschwindigkeit:
- Vorher: Neue Features benötigten Updates in mehreren Services
- Nachher: Ein SQL-Migration-File für neue Features
- Deploy-Zeit: Von 20 Minuten auf 3 Minuten reduziert
Alex’ Fazit nach einem Jahr:
“Ich hätte nie gedacht, dass ich mal alle meine Services durch Postgres ersetzen würde. Aber es funktioniert. Weniger Complexity, weniger Kosten, bessere Performance. Ich fokussiere mich wieder auf Features statt auf Infrastructure-Management. Postgres ist nicht nur eine Datenbank – es ist mein komplettes Backend.”
Lessons Learned:
- Start simple: Nicht jede App braucht von Tag 1 an Microservices
- Postgres first: Prüfe zuerst, ob Postgres + Extensions reichen
- Migration ist möglich: Auch bestehende Apps können schrittweise vereinfacht werden
- Kosten-Bewusstsein: Frühe Optimierung bei Tools spart später viel Geld
Wo Postgres-first glänzt – und wo nicht
Ideal für:
- Indie SaaS & MVPs – ein Stack, weniger Kosten
- Kleine Teams – weniger Ops-Aufwand
- Projekte mit vielen Features – Auth, Suche, Analytics, Jobs
- Prototyping – schnelle Iteration ohne Service-Setup
Weniger geeignet für:
- FAANG-Skala – Multi-Region, globale Latenz-Anforderungen
- Massive Blob-Speicherung – Videos, Petabyte-Objekte
- Extrem spezialisierte Anforderungen – z. B. hochskalierte ML-Pipelines
- Geografisch verteilte Teams – wenn lokale Latenz kritisch ist
Migrationsstrategie
Phase 1: Neue Features
- Alle neuen Features werden in Postgres implementiert
- Bestehende Services bleiben erstmal bestehen
Phase 2: Low-Risk Services
- Caching-Layer (Redis) → UNLOGGED TABLES
- Cronjobs → pg_cron
- Analytics → Event-Tables
Phase 3: Core Services
- Auth-System → pgcrypto + RLS
- Suche → TSVECTOR/pgvector
- Realtime → LISTEN/NOTIFY
Phase 4: Clean-up
- Alte Services abschalten
- Infrastructure vereinfachen
- Monitoring konsolidieren
Bottom Line
2025 fühlt es sich fast übertrieben an, für eine einfache App zehn verschiedene Tools hochzuziehen.
Mit Postgres + Extensions baust du ein Backend, das Jobs, Cache, Suche, Auth, AI und Analytics abdeckt.
Die Dev-Erfahrung bleibt simpel: Alles in SQL, weniger Services, weniger Rechnungen, weniger Fehlerquellen.
Merksatz: Statt 20 Tools: Ein Postgres, gut erweitert, reicht oft völlig aus.
Der erste Schritt: Schaue dir deine aktuelle Service-Liste an. Welcher Service könnte als nächstes durch eine Postgres-Extension ersetzt werden?
Die Zukunft gehört nicht komplexeren Stacks – sondern einfacheren.