Hier eine kompakte, praxisorientierte Übersicht zu PostgreSQL mit Fokus auf „Was ist anders als in Oracle?“ und „Was sollte ich vor dem Umstieg lernen?“. --- ## 1. Kurzüberblick & Gemeinsamkeiten Gemeinsamkeiten (nur kurz, da dir das meiste vertraut ist): - Relationales DBMS, SQL-basiert, ANSI-konform - [[ACID-Transaktionen]], [[MVCC]], Isolation Levels - Sequences, Views, [[Materialized Views]], Trigger, Stored Procedures/Functions - Joins, Subselects, Window Functions, [[CTEs]] (`WITH`), etc. - Rolle-/Rechtemodell, Schemas --- ## 2. Zentrale Unterschiede auf einen Blick Die wichtigsten Lernfelder im Übergang von Oracle zu PostgreSQL: 1. **Namensräume & `search_path` statt Synonyme** 2. **Datentypen & Funktionalität (z.B. `NUMERIC`, `SERIAL`, `JSONB`, Arrays)** 3. **Sequences & Identity-Spalten** 4. **PL/pgSQL vs. PL/SQL (kein Paketkonzept)** 5. **MVCC-Implementierung & VACUUM/Autovacuum** 6. **DDL in Transaktionen, Auto-Commit-Verhalten** 7. **Index-Typen & Besonderheiten (GIN/GiST, Partial-, Expression-Indexe)** 8. **Partitionierung (deutlich anders als ältere Oracle-Partitioning-Konzepte)** 9. **Admin & Tools (psql, Konfigurationsparameter, Monitoring)** --- ## 3. Schemata, Namensauflösung & Synonyme ### Schemata & `search_path` In PostgreSQL sind Schemata ähnlich wie in Oracle. Es gibt zusätzlich einen **`search_path`**, der festlegt, in welcher Reihenfolge Schemata nach Objekten durchsucht werden. ```sql SHOW search_path; SET search_path TO app, public; ``` Statt Synonymen (Oracle) wird oft mit `search_path` gearbeitet: - Kein `CREATE SYNONYM` in PostgreSQL. - Alternative: Views in einem „zentrale“ Schema, `search_path` setzen, oder `CREATE VIEW` als Abstraktionsschicht. **Lernpunkt:** Überleg dir, wie du Synonyme ablöst – meistens durch eine Kombination aus `search_path`, Views und ggf. konsistenter Schema-Namenskonvention. --- ## 4. Datentypen & SQL-Dialekt ### Wichtige Unterschiede bei Datentypen - `NUMBER` → in der Regel `NUMERIC(p,s)` oder `INTEGER`, `BIGINT`. - `VARCHAR2` → `VARCHAR(n)` oder `TEXT`. PostgreSQL hat keinen Unterschied zwischen `VARCHAR` und `VARCHAR2`. - `DATE` in PostgreSQL enthält Datum **und Uhrzeit** (wie Oracle `DATE`). Für „reine“ Datumswerte: `date`, für Zeitpunkte mit Zeitzone: `timestamptz`. - `CLOB`/`BLOB` → meist `TEXT` bzw. `BYTEA`. - Zusätzliche Typen: - `JSON`/`JSONB` - Arrays (`integer[]`, `text[]` etc.) - Geodaten (via Extension PostGIS) - `UUID`, `Inet`, `CIDR` etc. ```sql CREATE TABLE kunde ( id BIGSERIAL PRIMARY KEY, name VARCHAR(200), email TEXT, erstellt_am timestamptz DEFAULT now(), daten JSONB ); ``` ### Funktionen und Syntax-Details - String-Konkatenation: `||` (wie Oracle). - `NVL` → `COALESCE` (Standard); es gibt auch `NULLIF`. - `DECODE` → `CASE WHEN ... THEN ... ELSE ... END`. - `ROWNUM` → `LIMIT` / `OFFSET` oder Window Functions (`row_number()`). - Kein „`FROM dual`“ nötig, du kannst einfach: ```sql SELECT 1; ``` **Lernpunkt:** Zuordnen der wichtigsten Oracle-Funktionen zu PostgreSQL-Äquivalenten (`DECODE` → `CASE`, `NVL` → `COALESCE`, `ROWNUM` → `LIMIT`/Window). --- ## 5. Sequences & Identity-Spalten In Oracle: `CREATE SEQUENCE ...` + Trigger oder `IDENTITY` in neueren Versionen. In PostgreSQL gibt es mehrere Varianten: - Klassische Sequence: ```sql CREATE SEQUENCE myseq; SELECT nextval('myseq'); ``` - „Legacy“ Auto-Increment: ```sql CREATE TABLE t ( id SERIAL PRIMARY KEY, ... ); ``` - Standardkonforme [[Identity Columns]] (empfohlen): ```sql CREATE TABLE t ( id BIGINT GENERATED ALWAYS AS IDENTITY PRIMARY KEY, ... ); ``` **Lernpunkt:** Umstieg auf `GENERATED AS IDENTITY` planen, `SERIAL` verstehen (ist syntaktischer Zucker für Sequence + Default). --- ## 6. PL/pgSQL vs. PL/SQL (Packages, Prozeduren, Funktionen) ### Kein Paketkonzept PostgreSQL hat keine Packages wie Oracle (`package spec/body`). Stattdessen: - Funktionen stehen „flach“ in einem Schema. - Ähnliches Strukturieren über Namenskonventionen, Schemata, Extensions. ### PL/pgSQL Syntax ähnlich PL/SQL, aber mit einigen Unterschieden: ```sql CREATE OR REPLACE FUNCTION addiere(a int, b int) RETURNS int LANGUAGE plpgsql AS $$ DECLARE res int; BEGIN res := a + b; RETURN res; END; $$; ``` Ab PostgreSQL 11 gibt es auch **Stored Procedures** (ohne Rückgabewert, aufrufbar mit `CALL`) – im Unterschied zu Funktionen, die in SQL-Ausdrücke eingebettet werden können. **Lernpunkte:** - Unterschiede in Ausnahmebehandlung und Cursor-Syntax im Detail. - Kein Paket-Overloading wie in Oracle – Overloading geht, aber ohne Packages. - Migration von Package-Variablen: oft durch Tabellen, Konfigurationstabellen oder `SET LOCAL` + GUC-Parameter ersetzen. --- ## 7. Transaktionen, MVCC & Locks ### MVCC-Implementierung Beide nutzen MVCC, aber die Implementierung ist anders: - PostgreSQL speichert mehrere Versionen von Zeilen (Tuples) im Heap. - Gelöschte/veraltete Versionen werden nicht sofort entfernt, sondern durch **VACUUM** aufgeräumt. - Standard: Autovacuum kümmert sich darum. Manchmal Tuning nötig (`autovacuum_*`-Parameter). ### Isolation Levels Standard-Level in PostgreSQL ist `READ COMMITTED`, `REPEATABLE READ` ist nicht exakt wie Oracle `SERIALIZABLE`. Es gibt zusätzlich ein echtes `SERIALIZABLE` via SSI (Serializable Snapshot Isolation). ```sql SHOW default_transaction_isolation; SET SESSION CHARACTERISTICS AS TRANSACTION ISOLATION LEVEL REPEATABLE READ; ``` ### DDL in Transaktionen - PostgreSQL erlaubt DDL **innerhalb** von Transaktionen und kann diese zurückrollen: ```sql BEGIN; CREATE TABLE test (id int); ROLLBACK; -- Tabelle existiert danach nicht ``` - Standard-Clients (z.B. `psql`) arbeiten mit Auto-Commit = ON, aber du kannst das Verhalten steuern. **Lernpunkte:** - VACUUM/Autovacuum verstehen: wann notwendig, wie überwachen, wie konfigurieren. - Unterschiedliche Semantik von Isolation Levels im Detail prüfen (z.B. bei Portierung von Code, der sich auf Oracle-Sperrverhalten verlässt). --- ## 8. Indizes & Partitionierung ### Index-Typen PostgreSQL bietet mehr verschiedene Index-Methoden: - `btree` (Standard) - `hash` (seltener) - `GIN` (für Volltext, JSONB-Keys, Arrays) - `GiST` (Geodaten, Range-Typen) - `BRIN` (große append-only Tabellen, z.B. Logs) Zusätzlich: - **Expression Indexes**: ```sql CREATE INDEX idx_lower_name ON kunde (lower(name)); ``` - **Partial Indexes**: ```sql CREATE INDEX idx_active_kunden ON kunde (id) WHERE aktiv = true; ``` ### Partitionierung Neuere PostgreSQL-Versionen haben native Partitionierung (Range, List, Hash). Unterschied zu Oracle: - Implementierung anders, kein identisches Interface. - Viele Operationen laufen „Partition-transparent“, aber es gibt noch Ecken (z.B. bestimmte DDL-Operationen). ```sql CREATE TABLE messwerte ( id BIGINT GENERATED ALWAYS AS IDENTITY, ts timestamptz NOT NULL, wert numeric ) PARTITION BY RANGE (ts); CREATE TABLE messwerte_2024 PARTITION OF messwerte FOR VALUES FROM ('2024-01-01') TO ('2025-01-01'); ``` **Lernpunkte:** - Eignung und Grenzen von GIN/GiST verstehen, wenn du JSONB oder Volltext planst. - Partitionierungsstrategie neu durchdenken, statt 1:1 die Oracle-Logik zu kopieren. --- ## 9. Materialized Views PostgreSQL hat Materialized Views, aber: - Kein `ON COMMIT REFRESH`. - Refresh ist explizit: ```sql REFRESH MATERIALIZED VIEW my_mv; ``` - Optional mit `CONCURRENTLY` (mit Einschränkungen), um Downtime zu minimieren. **Lernpunkt:** Wenn du in Oracle stark auf automatische Refresh-Mechanismen setzt, brauchst du in PostgreSQL einen eigenen Refresh-Workflow (z.B. Cron, Scheduler, Applikationslogik). --- ## 10. Rechte & Rollenmodell Ähnlich, aber mit eigenen Begriffen/Details: - Nur **Rollen** (kein getrenntes Konzept von „User“ und „Role“ wie in Oracle; ein User ist eine Login-fähige Rolle). - Rechte auf Objekte (`GRANT SELECT ON table TO role;` etc.) - Kein systemweites `PUBLIC SYNONYM`, aber es gibt das Schema `public` und das `PUBLIC`-Rolle/Privileges-Konzept. ```sql CREATE ROLE app_user LOGIN PASSWORD '...'; GRANT CONNECT ON DATABASE mydb TO app_user; GRANT USAGE ON SCHEMA app TO app_user; GRANT SELECT, INSERT, UPDATE, DELETE ON ALL TABLES IN SCHEMA app TO app_user; ``` **Lernpunkt:** Mapping deiner bisherigen Oracle-Rollen/Profiles auf PostgreSQL-Rollen und -Rechte. --- ## 11. Administration, Tools & Ökosystem ### Wichtige Tools - `psql` (Kommandozeile, sehr mächtig) - Admin-Tools: `pgAdmin`, `DBeaver`, `DataGrip` etc. - Verbindungs-Pooler (wichtig, da PostgreSQL pro Verbindung einen Prozess startet): - `pgbouncer`, `pgpool-II` ### Wichtige Admin-Konzepte - **Konfiguration** über `postgresql.conf` und `ALTER SYSTEM`: z.B. `shared_buffers`, `work_mem`, `maintenance_work_mem`, `max_connections`. - **VACUUM/ANALYZE**: - `VACUUM` räumt auf. - `ANALYZE` aktualisiert Statistiken. - **EXPLAIN/EXPLAIN ANALYZE**: zwingend für Performance-Tuning. ```sql EXPLAIN ANALYZE SELECT ... FROM ... WHERE ...; ``` - **Backup/Recovery**: - Logische Backups: `pg_dump`, `pg_dumpall`. - Physische Backups & PITR: Base-Backups + WAL-Archiving (oder Tools wie `pgBackRest`). **Lernpunkte:** - Verbindungspooling ist viel wichtiger als in Oracle. - Autovacuum-Monitoring (z.B. via `pg_stat_*`-Views) und Basiskonfiguration. --- ## 12. Typische Stolpersteine beim Umstieg 1. **Fehlende Synonyme** → Lösung über `search_path`, Views, klare Schema-Strategie. 2. **Paketkonzept fehlt** → Namespacing neu denken. 3. **Materialized View Refresh** → eigene Scheduler-Logik. 4. **ROWNUM/`dual`** → an `LIMIT`/`OFFSET`, Window Functions, `SELECT 1;` gewöhnen. 5. **Datenbanklinks (`DBLINK`)** → Extension `dblink` oder `postgres_fdw` (Foreign Data Wrapper) verwenden. 6. **Autoincrement** → `IDENTITY`/`SERIAL` + `currval()/nextval()`-Verwendung lernen. 7. **Optimizer-Verhalten** → Statistiken, Parameter und Query-Pläne sind anders; alte „Index-Hints-Gewohnheiten“ greifen nicht 1:1. --- ## 13. Sinnvolle Lernreihenfolge 1. Basiskonzepte: - Schemata + `search_path` - Datentyp-Mapping (NUMBER, DATE, CLOB/BLOB → NUMERIC, TIMESTAMP, TEXT/BYTEA) - Sequences & Identity 2. SQL-Dialekt: - Funktionale Unterschiede (`DECODE`, `NVL`, `ROWNUM`, `dual`, Subqueries) 3. Server-seitige Logik: - PL/pgSQL, Unterschiede zu PL/SQL, kein Package-Konzept 4. MVCC & Performance: - VACUUM/Autovacuum, EXPLAIN ANALYZE, Index-Typen 5. Admin & Betrieb: - Rollen, Backups, Konfiguration, Verbindungspooling 6. Spezielle Features: - JSONB, Arrays, GIN-Indizes, Partitionierung, FDWs Wenn du magst, kannst du mir ein paar typische Oracle-Features nennen, die du intensiv nutzt (z.B. bestimmte Partitionierungsarten, Advanced Queuing, bestimmte PL/SQL-Patterns). Dann kann ich dir eine gezielte „Mapping-Tabelle“ für genau diese Themen in PostgreSQL machen.