DynamoDB Throttling — warum es passiert und wie du es behebst
Drosselung ist DynamoDBs Art, dir zu sagen, dass ein Limit erreicht wurde — aber es gibt vier verschiedene Limits, drei verschiedene Exceptions, und die Lösung für die eine Ursache verschlimmert eine andere. Die Tabellenkapazität zu erhöhen bringt bei einem heißen Schlüssel nichts; auf On-Demand zu wechseln bringt bei einem heißen Schlüssel ebenfalls nichts und kann nach eigenen Regeln trotzdem drosseln. Dieser Guide ist das Dach über allem: welches Limit du tatsächlich getroffen hast, wie die Metriken sie auseinanderhalten, und die Lösung, die zu jeder Ursache passt.
Warum drosselt DynamoDB meine Anfragen?
Einer von vier dokumentierten Gründen: Eine einzelne Partition hat ihr festes Limit pro Partition von 3.000 Read Units bzw. 1.000 Write Units pro Sekunde überschritten (ein heißer Schlüssel — passiert in beiden Kapazitätsmodi); die Tabelle hat ihre provisionierten RCU/WCU überschritten (Provisioned-Modus); das Konto hat sein regionales Durchsatzkontingent überschritten; oder eine On-Demand-Tabelle ist innerhalb von 30 Minuten schneller gewachsen als auf das Doppelte ihrer bisherigen Spitze. Die Lösung hängt davon ab, welcher es war — diagnostiziere also, bevor du irgendetwas neu dimensionierst.
Die vier Drosselungs-Szenarien
AWS' eigene Troubleshooting-Seite teilt Drosselung in genau vier Fälle auf:
- Durchsatz eines Key-Range (einer Partition) überschritten — beide Modi. Jede Partition ist auf maximal 3.000 Read Units und 1.000 Write Units pro Sekunde (Partition-Key-Doku) ausgelegt, und die Item-Größe zählt dagegen. Keine Einstellung auf Tabellenebene hebt das an; nur das Schlüsseldesign verteilt es. Das ist der Fall heiße Partition, und die Tabelle kann massiv unterausgelastet aussehen, während sie drosselt.
- Provisionierter Durchsatz überschritten — Provisioned-Modus. Der Verbrauch hat die provisionierten RCU/WCU der Tabelle (oder eines GSI) geschlagen, und das ~5-minütige Polster der Burst Capacity war aufgebraucht. Die Leiter der Lösungen liegt auf der Kapazitätsseite: Auto-Scaling, eine höhere Provisionierung oder ein Moduswechsel.
- Kontingent auf Kontoebene überschritten. Regionale Kontingente pro Konto deckeln den Gesamtdurchsatz — standardmäßig 40.000 Read und 40.000 Write Units pro Tabelle und für den Provisioned-Modus 80.000 RCU und 80.000 WCU pro Konto (Kontingente); das sind Anfangswerte, über Service Quotas anpassbar, und On-Demand-Tabellen haben kein Durchsatzkontingent auf Kontoebene.
- Maximaler On-Demand-Durchsatz überschritten. On-Demand nimmt sofort bis zum Doppelten der bisherigen Spitze auf; wächst du innerhalb von 30 Minuten über das Doppelte hinaus, kann es drosseln (On-Demand-Doku). Neue On-Demand-Tabellen halten ab Werk 4.000 Writes/s und 12.000 Reads/s aus. Für eine geplante Stufenspitze (Launch, Sale, Migration) wärmst du die Tabelle besser mit Warm Throughput vor, statt zu hoffen, dass die Rampe flach genug ist.
Die drei Exceptions und das Feld, das die Ursache benennt
ProvisionedThroughputExceededException— Drosselung der Kapazität im Provisioned-Modus: „du hast deinen maximal zulässigen provisionierten Durchsatz für eine Tabelle oder für einen oder mehrere Global Secondary Indexes überschritten“. Details auf der eigenen Fehlerseite.ThrottlingException— zu schnell abgesetzte Control-Plane-Operationen und, auf On-Demand-Tabellen, jede Data-Plane-Operation, deren Rate zu hoch ist (das ist die Exception hinter der Doppelte-Spitze-Regel — siehe die On-Demand-Fehlerseite und ThrottlingException).RequestLimitExceeded— Durchsatzlimits auf Kontoebene: Terrain des „wende dich an den AWS Support“, behandelt auf seiner Fehlerseite.
Alle drei sind als wiederholbar markiert, und alle drei tragen inzwischen
strukturierte ThrottlingReason-Werte der Form Ressource + Operation +
Limit — TableReadProvisionedThroughputExceeded,
IndexWriteKeyRangeThroughputExceeded, TableWriteAccountLimitExceeded und so
weiter (Fehlerreferenz).
Lies den Grund, nicht nur die Exception-Klasse: Er benennt die Ressource
(Tabelle oder Index), die Richtung der Operation und welches der vier Limits du
getroffen hast — und genau das ist die Diagnose. Eine Einschränkung erzwingt die
Doku selbst: AWS-Seiten sind sich uneins, ob Drosselung durch Kontolimits als
RequestLimitExceeded auftaucht oder als ThrottlingException mit einem
AccountLimitExceeded-Grund — richte deine Behandlung also am Reason-String
aus.
Was Last abfängt, bevor du gedrosselt wirst
Zwei eingebaute Mechanismen federn die Limits ab, und ihre Grenzen zu kennen erklärt das „gestern ging es doch“:
- Burst Capacity hält bis zu fünf Minuten (300 Sekunden) ungenutzter Lese- und Schreibkapazität für Spitzen bereit — aber DynamoDB kann sie „ohne vorherige Ankündigung“ auch für Hintergrundwartung verbrauchen, und AWS weist ausdrücklich darauf hin, dass sich die Details ändern können. Plane nicht mit Burst; behandle es als Glück.
- Adaptive Capacity verschiebt Durchsatz automatisch und sofort in Richtung heißer Partitionen und kann ein häufig aufgerufenes Item auf eine eigene Partition isolieren — aber nur, „sofern der Traffic die gesamte provisionierte Kapazität deiner Tabelle oder die maximale Kapazität der Partition nicht überschreitet“. Es gleicht Schieflage aus; es hebt die Obergrenze von 3.000/1.000 pro Partition nie an, und es spaltet keine Item-Collections, wenn die Tabelle einen LSI hat. Die aktuellen AWS-Troubleshooting-Seiten stützen sich auf Split-for-Heat — Partitionen, die sich unter anhaltender Hitze aufteilen —, was Zeit braucht und bei einem einzelnen heißen Schlüssel nicht hilft.
Diagnostiziere es über die Metriken
CloudWatch trennt Requests von Events, und diese Unterscheidung erledigt die Diagnose (Metrik-Referenz):
ThrottledRequestszählt eine Anfrage einmal, wenn irgendein Event in ihr gedrosselt wurde — einPutItemauf eine Tabelle mit drei GSIs ist eine Anfrage, aber vier Write-Events. In einem Batch erhöht sich der Zähler nur, wenn jedes Item gedrosselt wurde.ReadThrottleEvents/WriteThrottleEventszählen jedes gedrosselte Event — einBatchGetItemüber 10 Items sind 10GetItem-Events. Um die Write-Drosselungen eines GSI zu sehen, musst du die Metrik mitTableNameundGlobalSecondaryIndexNameabfragen — so versteckt sich GSI-Gegendruck vor Dashboards auf Tabellenebene.- Die neueren ursachenspezifischen Event-Metriken
(
WriteProvisionedThroughputThrottleEvents,ReadKeyRangeThroughputThrottleEvents,…AccountLimitThrottleEvents,…MaxOnDemandThroughputThrottleEvents) teilen die Zählwerte nach denselben vier Ursachen auf — wenn deine Region sie zeigt, beantworten sie die Frage „welches Limit“ direkt.
Eine Falle: SDKs wiederholen gedrosselte Anfragen automatisch — der Standard-Retry-Modus macht standardmäßig 3 Versuche insgesamt (der Opt-in-Retry-Rollout von 2026 stellt die DynamoDB-Clients auf 4 Versuche mit engeren Wartezeiten um). Leichte Drosselung zeigt sich deshalb als Latenz, nicht als Fehler; beobachte die Drosselungs-Metriken, nicht nur deine Exception-Logs.
GSI-Gegendruck: die Drosselung, die auf die falsche Tabelle zeigt
Wenn irgendein GSI die Schreibverstärkung nicht aufnehmen kann, „drosselt
DynamoDB die Schreibvorgänge in die Basistabelle, um die Datenkonsistenz zu
wahren“
(GSI-Drosselungs-Doku)
— selbst dann, wenn die Basistabelle Kapazität übrig hat. Der ResourceArn der
Exception zeigt auf den Index, aber die Operation, die gescheitert ist, ist dein
Schreibvorgang in die Basistabelle. Jeder Index braucht seinen eigenen
Kapazitätsplan (und seine eigene
Auto-Scaling-Policy);
warum ein GSI Basistabellen-Writes drosselt
geht die Mechanik durch.
Die Lösung zur Ursache passend wählen
| Ursache | Was hilft | Was nicht hilft |
|---|---|---|
| Heißer Schlüssel / heiße Partition | Schlüsseldesign, das die Last verteilt (Hot Partitions); Zeit für Split-for-Heat | Tabellenkapazität erhöhen, auf On-Demand wechseln |
| Provisionierte Kapazität | Auto-Scaling, höheres Minimum oder On-Demand | Retries allein — sie erzeugen zusätzliche Last |
| GSI-Gegendruck | Den Index skalieren; Sparse-Index oder Projektion ändern | Die Basistabelle skalieren |
| Kontingent des Kontos | Erhöhung über Service Quotas | Einstellungen auf Tabellenebene |
| On-Demand-Stufenspitze | Vorwärmen (Warm Throughput); die Rampe über 30+ Minuten strecken | Warten — die Doppelte-Spitze-Grenze sinkt nur langsam |
In DynoTable umsetzen
Die meiste selbstverschuldete Drosselung beginnt mit Lesevorgängen, die mehr
kosten, als sie aussehen: Ein gefilterter Scan verbraucht den vollen
Lesevorgang so oder so. DynoTables Kostenvorschau vor dem Ausführen zeigt, ob
aus einem Statement ein Query oder ein Scan wird, welchen Index es trifft
und welche Lesekosten geschätzt anfallen, bevor du sie ausgibst — die günstigste
Lösung gegen Drosselung ist der teure Lesevorgang, den du nicht ausgeführt hast.
Der Guide Scan vs. Query behandelt den Unterschied; der
kostenlose Item-Größen-Rechner macht aus
einem echten Item die RCU/WCU-Zahlen, in denen die Limits oben gemessen werden.
Fallstricke und nächste Schritte
- Retries verstärken die Überlast. Backoff ist in die SDKs eingebaut, aber eine enge Retry-Schleife auf Anwendungsebene obendrauf vervielfacht den Druck auf genau die Partition, die ohnehin kämpft.
- Batches verstecken teilweise Drosselung. Ein
BatchWriteItemgibt unverarbeitete Items zurück, statt zu werfen, solange irgendein Item durchgeht — prüfeUnprocessedItems, nicht nur Exceptions. - Die Sicht auf Tabellenebene lügt über GSIs. Zeichne Throttle-Events immer pro Index; Dashboards der Basistabelle sehen während Gegendruck sauber aus.
- Kapazitätslösungen brauchen Minuten; Schlüsseldesign hält ewig. Auto-Scaling reagiert in ~5 Minuten, Kontingenterhöhungen brauchen ein Support-Ticket, aber ein heißer Schlüssel folgt dir in jeden Kapazitätsmodus — steck die Mühe dorthin, wo sie sich verzinst: wie Partition Keys funktionieren.
Lade DynoTable herunter, um den Scan-vs-Query-Plan und die Lesekosten jeder Query zu sehen, bevor sie gegen deine Kapazität läuft.