Die Verteilung großer Datenmengen erfolgt auf zwei Hauptarten:
Partitionierung (partitioning): Logische Aufteilung einer Tabelle innerhalb einer Datenbank in Segmente (Partition) nach einem bestimmten Schlüssel, meist Datum oder Wertebereich. Dies ermöglicht schnelle Operationen an einzelnen Partitionen, beschleunigt die Suche und erleichtert die Wartung.
Sharding (sharding): Physische Aufteilung der Daten auf mehrere Datenbanken/Server nach einem bestimmten Algorithmus — die Tabelle wird tatsächlich auf verschiedenen Clustern dupliziert, von denen jeder sein eigenes Datensegment enthält.
Vorteile der Partitionierung — keine Notwendigkeit, separate Geschäftslogik für die Routen der Abfragen zu unterstützen, alles geschieht "transparent" für die Anwendung; Nachteile — beschränkt durch die Möglichkeiten einer einzelnen DBMS.
Sharding ermöglicht horizontale Skalierung (das Limit hängt nur von der Anzahl der Server ab), erfordert jedoch komplexe Synchronisation, Routing und Verarbeitung von "inter-shard"-Abfragen.
-- Basis-Partitionstabelle CREATE TABLE orders ( id SERIAL PRIMARY KEY, customer_id INT, order_date DATE ) PARTITION BY RANGE (order_date); CREATE TABLE orders_2023 PARTITION OF orders FOR VALUES FROM ('2023-01-01') TO ('2024-01-01');
Frage: Kann man "im laufenden Betrieb" Zeilen zwischen Partitionen verschieben, ohne die Haupttabelle zu sperren?
Antwort: In den meisten DBMS ist das Verschieben einer Zeile zwischen Partitionen äquivalent zu Löschen und Einfügen — solche Operationen können Zeilen und sogar die gesamte Tabelle sperren, insbesondere wenn dabei Trigger oder Fremdschlüssel beteiligt sind. Dies muss bei massiven "Rollbacks" von Daten zwischen Partitionen berücksichtigt werden.
-- ALTER TABLE ... MOVE PARTITION erfordert in der Regel besondere Vorsicht bei Sperren. Am besten zu Zeiten mit geringer Auslastung durchführen.
Geschichte 1: Im Projekt wurden analytische Berichte über alle Partitionen gleichzeitig erstellt, ohne zu berücksichtigen, dass eine partitionierte Tabelle mit Tausenden von Partitionen gewaltige Ausführungspläne erzeugte. Das Ergebnis — ein plötzlicher Anstieg der Ausführungszeiten und der Serverlast. Lösung: Anzahl der Partitionen erhöhen, die den tatsächlichen Geschäftsdimensionen der Abfrage entsprechen, und die Scanpläne optimieren.
Geschichte 2: Bei der Einführung von Sharding wurde die Nicht-Eindeutigkeit der Identifikatoren zwischen den Shards nicht berücksichtigt. Oft traten Schlüsselkonflikte bei der Aggregation zwischen Shards auf.
Geschichte 3: Automatische Archivierung von "veralteten" Partitionen entfernte diese ohne erneute Überprüfung der Fremdbeziehungen, was zu einem Verlust der Verknüpfung mit anderen Tabellen und einem Verlust eines Teils der "lebenden" Daten führte. Danach wurde die gesamte Logik zur Löschung von Partitionen mit Multitests zur Konsistenz neu geschrieben.