DynamoDB Capacity Modes: Provisioned vs. On-Demand – Throttling vermeiden und Kosten optimieren

Du startest ein neues Projekt, hast aber noch keine belastbaren Traffic-Daten – und fragst dich, ob du mit Provisioned Capacity zu wenig reservierst und Throttling riskierst, oder mit On-Demand zu viel zahlst. DynamoDB Capacity Modes sind der erste Hebel, den du richtig stellen musst, bevor du überhaupt anfängst, Tabellen zu designen.

TL;DR – DynamoDB Capacity Modes auf einen Blick

KriteriumOn-DemandProvisioned
Traffic-Muster bekannt?Nein / unvorhersehbarJa / stabil
Throttling-RisikoSehr geringBei Fehlkonfiguration hoch
Kosten bei stabilem TrafficHöherGünstiger
Auto Scaling erforderlichNeinEmpfohlen
ModuswechselEinmal alle 24 StundenEinmal alle 24 Stunden
Typischer EinsatzNeue Apps, Spikes, Dev/TestProduktion mit bekanntem Muster

Wie DynamoDB Capacity Modes funktionieren

Bevor du den richtigen Modus wählst, musst du verstehen, wie DynamoDB intern Kapazität verwaltet – sonst optimierst du am falschen Hebel.

DynamoDB misst Lese- und Schreiboperationen in Request Units: eine Read Request Unit (RRU) entspricht einem stark konsistenten Lesevorgang für ein Item bis 4 KB, eine Write Request Unit (WRU) einem Schreibvorgang für ein Item bis 1 KB. Beide Modi bauen auf diesem Modell auf – sie unterscheiden sich nur darin, wie Kapazität reserviert und abgerechnet wird.

Provisioned Mode

  1. Du legst explizit Read Capacity Units (RCU) und Write Capacity Units (WCU) pro Sekunde fest.
  2. DynamoDB hält diese Kapazität dauerhaft bereit – du zahlst dafür, unabhängig davon, ob du sie nutzt.
  3. Jede Partition bekommt einen gleichmäßigen Anteil der bereitgestellten Kapazität. Überschreitet eine Partition ihr Limit, greift DynamoDB zunächst auf Burst-Kapazität zurück – ein Pool nicht genutzter Kapazität aus den letzten 300 Sekunden – um Throttling zu verhindern. Ist auch dieser Pool erschöpft, gibt DynamoDB ProvisionedThroughputExceededException zurück.
  4. Mit Auto Scaling kannst du RCU/WCU automatisch innerhalb definierter Grenzen anpassen lassen.

On-Demand Mode

  1. Du reservierst keine Kapazität. DynamoDB skaliert automatisch auf den aktuellen Traffic.
  2. Abgerechnet wird pro tatsächlich genutzter RRU/WRU.
  3. Es gibt eine interne Previous Peak-Grenze: DynamoDB kann sofort auf das Doppelte des bisherigen Peaks skalieren. Darüber hinaus skaliert der Dienst ebenfalls, aber nicht instantan.
graph LR Client(["Client"]) Client --> Router["DynamoDB Router"] Router --> ProvCheck{"Provisioned Mode?"} ProvCheck -- Ja --> CapCheck{"Kapazität verfügbar?"} CapCheck -- Ja --> Success1["✓ Response"] CapCheck -- Nein --> Burst{"Burst-Kapazität verfügbar?"} Burst -- Ja --> Success2["✓ Response (Burst genutzt)"] Burst -- Nein --> Throttle["✗ Throttling ProvisionedThroughputExceededException"] ProvCheck -- Nein --> OnDemand["On-Demand Automatische Skalierung"] OnDemand --> Success3["✓ Response"]
  1. Client-Request trifft die DynamoDB-Partition.
  2. Im Provisioned Mode wird geprüft, ob die bereitgestellte Kapazität ausreicht. Falls nicht, greift Burst-Kapazität. Ist auch diese erschöpft, folgt Throttling.
  3. Im On-Demand Mode entfällt diese Prüfung – DynamoDB skaliert intern und gibt das Ergebnis direkt zurück.

Entscheidungsbaum: Welcher DynamoDB Capacity Mode passt zu dir?

Die Wahl hängt nicht nur vom Budget ab, sondern vom Verhältnis zwischen Traffic-Vorhersagbarkeit und Kostentoleranz.

graph TD Start(["Neues DynamoDB-Projekt"]) Start --> Q1{"Traffic-Muster bekannt?"} Q1 -- Nein --> Q2{"Dev/Test oder Produktion?"} Q2 -- Dev/Test --> OnDemand1["On-Demand PAY_PER_REQUEST"] Q2 -- Produktion --> OnDemand2["On-Demand starten dann Metriken sammeln"] OnDemand2 --> Monitor["2 Wochen CloudWatch beobachten"] Monitor --> Q3{"Stabiles Muster?"} Q3 -- Nein --> OnDemand2 Q3 -- Ja --> Provisioned["Wechsel zu Provisioned + Auto Scaling"] Q1 -- Ja --> Q4{"Große Spikes erwartet?"} Q4 -- Ja --> AutoScale["Provisioned + Auto Scaling konservativ konfigurieren"] Q4 -- Nein --> ProvisionedDirekt["Provisioned + Auto Scaling"]
  1. Wenn Traffic-Muster unbekannt oder stark schwankend sind, ist On-Demand der sichere Einstieg.
  2. Sobald du stabile Baseline-Metriken aus CloudWatch hast, lohnt sich der Wechsel zu Provisioned mit Auto Scaling.
  3. Für Dev/Test-Umgebungen mit sporadischem Zugriff bleibt On-Demand meist günstiger, auch langfristig.

On-Demand Capacity konfigurieren

On-Demand ist der einfachere Einstieg – keine Kapazitätsplanung, kein Auto Scaling einrichten.

Neue Tabelle mit On-Demand erstellen

aws dynamodb create-table \
  --table-name MeineTabelle \
  --attribute-definitions AttributeName=PK,AttributeType=S \
  --key-schema AttributeName=PK,KeyType=HASH \
  --billing-mode PAY_PER_REQUEST \
  --region us-east-1

Der Parameter --billing-mode PAY_PER_REQUEST aktiviert On-Demand. Du gibst keine RCU/WCU an – das wäre bei diesem Modus auch ein Fehler.

Bestehende Tabelle auf On-Demand umstellen

aws dynamodb update-table \
  --table-name MeineTabelle \
  --billing-mode PAY_PER_REQUEST \
  --region us-east-1

Aktuellen Modus prüfen

aws dynamodb describe-table \
  --table-name MeineTabelle \
  --region us-east-1 \
  --query 'Table.BillingModeSummary'

Provisioned Capacity mit Auto Scaling konfigurieren

Provisioned ohne Auto Scaling ist in der Praxis riskant – du planst für den Peak, zahlst aber immer. Auto Scaling löst dieses Problem, indem es RCU/WCU innerhalb definierter Grenzen dynamisch anpasst.

Tabelle mit Provisioned Capacity erstellen

aws dynamodb create-table \
  --table-name MeineTabelle \
  --attribute-definitions AttributeName=PK,AttributeType=S \
  --key-schema AttributeName=PK,KeyType=HASH \
  --billing-mode PROVISIONED \
  --provisioned-throughput ReadCapacityUnits=5,WriteCapacityUnits=5 \
  --region us-east-1

Auto Scaling für Write Capacity einrichten

🔽 Auto Scaling Konfiguration anzeigen (3 Schritte)

Schritt 1: Scalable Target registrieren

aws application-autoscaling register-scalable-target \
  --service-namespace dynamodb \
  --resource-id 'table/MeineTabelle' \
  --scalable-dimension dynamodb:table:WriteCapacityUnits \
  --min-capacity 5 \
  --max-capacity 100 \
  --region us-east-1

Schritt 2: Scaling Policy erstellen

aws application-autoscaling put-scaling-policy \
  --service-namespace dynamodb \
  --resource-id 'table/MeineTabelle' \
  --scalable-dimension dynamodb:table:WriteCapacityUnits \
  --policy-name MeineTabelle-WCU-ScalingPolicy \
  --policy-type TargetTrackingScaling \
  --target-tracking-scaling-policy-configuration '{
    "TargetValue": 70.0,
    "PredefinedMetricSpecification": {
      "PredefinedMetricType": "DynamoDBWriteCapacityUtilization"
    }
  }' \
  --region us-east-1

Schritt 3: Konfiguration prüfen

aws application-autoscaling describe-scalable-targets \
  --service-namespace dynamodb \
  --resource-ids 'table/MeineTabelle' \
  --region us-east-1

Der Target-Wert von 70 % ist ein gängiger Ausgangspunkt – er lässt genug Puffer, damit Auto Scaling hochskalieren kann, bevor Throttling einsetzt. Bei sehr spiky Traffic solltest du diesen Wert eher auf 50–60 % senken.

IAM-Berechtigungen für Capacity-Management

Wer Tabellen erstellt oder den Billing-Mode ändert, braucht explizite Berechtigungen. Besonders application-autoscaling wird häufig vergessen.

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "dynamodb:CreateTable",
        "dynamodb:UpdateTable",
        "dynamodb:DescribeTable"
      ],
      "Resource": "arn:aws:dynamodb:us-east-1:123456789012:table/MeineTabelle"
    },
    {
      "Effect": "Allow",
      "Action": [
        "application-autoscaling:RegisterScalableTarget",
        "application-autoscaling:PutScalingPolicy",
        "application-autoscaling:DescribeScalableTargets",
        "application-autoscaling:DescribeScalingPolicies"
      ],
      "Resource": "*"
    }
  ]
}

application-autoscaling-Aktionen erfordern Resource: * – das ist eine dokumentierte Einschränkung des Service Authorization Reference, keine Nachlässigkeit.

Wechsel zwischen den Modi – was du wissen musst

Du kannst zwischen On-Demand und Provisioned wechseln, aber maximal einmal alle 24 Stunden. Das klingt harmlos, wird aber zum Problem, wenn du planst, den Modus als reaktiven Kostenhebel zu nutzen.

Stell dir den Moduswechsel wie einen Neustart des Kapazitätsmodells vor – DynamoDB muss intern umkonfigurieren. Deshalb ist er auf einmal alle 24 Stunden begrenzt, nicht auf Knopfdruck verfügbar.

Praktische Konsequenz: Wenn du morgens auf Provisioned wechselst und abends ein unerwarteter Traffic-Spike kommt, kannst du nicht einfach zurück zu On-Demand wechseln. Plane den Wechsel daher bewusst – idealerweise nach einer stabilen Beobachtungsphase von mindestens zwei Wochen.

Moduswechsel durchführen

aws dynamodb update-table \
  --table-name MeineTabelle \
  --billing-mode PROVISIONED \
  --provisioned-throughput ReadCapacityUnits=10,WriteCapacityUnits=10 \
  --region us-east-1

Zeitpunkt des letzten Wechsels prüfen

aws dynamodb describe-table \
  --table-name MeineTabelle \
  --region us-east-1 \
  --query 'Table.BillingModeSummary.LastUpdateToPayPerRequestDateTime'

Throttling diagnostizieren – der häufigste Fehler in der Praxis

Hier ist ein Muster, das ich mehrfach gesehen habe: Eine Tabelle läuft wochenlang stabil im Provisioned Mode. Dann gibt es einen Deployment-bedingten Traffic-Spike – und plötzlich tauchen ProvisionedThroughputExceededException-Fehler in den Logs auf. Die erste Reaktion: Auto Scaling überprüfen. Aber Auto Scaling war korrekt konfiguriert.

Die eigentliche Ursache war ein Hot Partition-Problem: Der neue Feature-Code schrieb alle neuen Einträge mit demselben Partition Key-Präfix. DynamoDB verteilte die Last nicht gleichmäßig – eine einzelne Partition wurde überlastet, während andere leer blieben. Auto Scaling hilft hier nicht, weil es die Gesamtkapazität erhöht, aber nicht die Verteilung korrigiert.

graph TD Symptom["WriteThrottleEvents in CloudWatch"] Symptom --> Diag1{"ConsumedWCU nahe am Provisioned-Limit?"} Diag1 -- Ja --> Fix1["Kapazität erhöhen oder On-Demand wechseln"] Diag1 -- Nein --> Diag2{"Gleichmäßige Partitionsverteilung?"} Diag2 -- Nein --> HotPartition["Hot Partition Problem Partition Key überdenken"] Diag2 -- Ja --> Diag3{"Auto Scaling konfiguriert?"} Diag3 -- Nein --> Fix2["Auto Scaling einrichten"] Diag3 -- Ja --> Fix3["Target-Wert senken z.B. 50-60%"]

Throttling-Metriken in CloudWatch prüfen

aws cloudwatch get-metric-statistics \
  --namespace AWS/DynamoDB \
  --metric-name WriteThrottleEvents \
  --dimensions Name=TableName,Value=MeineTabelle \
  --start-time 2024-01-15T00:00:00Z \
  --end-time 2024-01-15T23:59:59Z \
  --period 300 \
  --statistics Sum \
  --region us-east-1

Consumed vs. Provisioned Capacity vergleichen

aws cloudwatch get-metric-statistics \
  --namespace AWS/DynamoDB \
  --metric-name ConsumedWriteCapacityUnits \
  --dimensions Name=TableName,Value=MeineTabelle \
  --start-time 2024-01-15T00:00:00Z \
  --end-time 2024-01-15T23:59:59Z \
  --period 300 \
  --statistics Sum \
  --region us-east-1

Wenn WriteThrottleEvents auftauchen, obwohl ConsumedWriteCapacityUnits weit unter dem Provisioned-Limit liegt, ist das ein klares Indiz für ein Hot-Partition-Problem – kein Kapazitätsproblem. In diesem Fall hilft weder mehr RCU/WCU noch ein Wechsel zu On-Demand. Du musst den Partition Key überdenken.

Throttling trotz ausreichender Gesamtkapazität ist fast immer ein Datenmodell-Problem, kein Kapazitätsmodus-Problem.

Kosten vergleichen – wann lohnt sich der Wechsel zu Provisioned?

On-Demand ist komfortabel, aber bei konstantem Traffic teurer als Provisioned mit Auto Scaling. Die genauen Preise variieren je nach Region – prüfe immer die aktuelle AWS DynamoDB Pricing-Seite. Als Faustregel gilt: Wenn deine CloudWatch-Metriken über zwei Wochen hinweg eine stabile Baseline ohne große Spikes zeigen, ist Provisioned mit Auto Scaling wirtschaftlicher.

Nutze den AWS Cost Explorer, um tatsächliche Kosten beider Modi zu vergleichen, bevor du wechselst.

aws ce get-cost-and-usage \
  --time-period Start=2024-01-01,End=2024-01-31 \
  --granularity MONTHLY \
  --filter '{
    "Dimensions": {
      "Key": "SERVICE",
      "Values": ["Amazon DynamoDB"]
    }
  }' \
  --metrics BlendedCost \
  --region us-east-1

Fazit und nächste Schritte mit DynamoDB Capacity Modes

Wenn du Traffic-Muster noch nicht kennst: Starte mit On-Demand. Du vermeidest Throttling, musst keine Kapazität planen, und zahlst nur für das, was du nutzt. Sobald du zwei Wochen CloudWatch-Daten hast und ein stabiles Muster erkennst, wechsle zu Provisioned mit Auto Scaling – das ist in der Regel der günstigere Betriebsmodus für Produktionsworkloads.

Der Moduswechsel kostet dich einmal alle 24 Stunden – plane ihn bewusst, nicht reaktiv. Und wenn Throttling auftritt, prüfe zuerst die Partition-Key-Verteilung, bevor du Kapazität erhöhst.

Glossar

BegriffBedeutung
RCU / WCURead/Write Capacity Unit – Maßeinheit für bereitgestellte Kapazität im Provisioned Mode
RRU / WRURead/Write Request Unit – Maßeinheit für tatsächlich verbrauchte Kapazität im On-Demand Mode
Burst-KapazitätNicht genutzte Provisioned-Kapazität der letzten 300 Sekunden, die DynamoDB bei kurzfristigen Spikes einsetzt, um Throttling zu verhindern
Hot PartitionEine einzelne DynamoDB-Partition, die überproportional viel Traffic erhält – häufigste Ursache für Throttling trotz ausreichender Gesamtkapazität
ProvisionedThroughputExceededExceptionFehler, den DynamoDB zurückgibt, wenn Provisioned Capacity und Burst-Kapazität erschöpft sind

Kommentare