Blog

AWS Cost Traps

4 min Lesezeit
aws cost-optimization cloud

Jedes AWS-Tutorial zeigt dir die Kosten des Services den du baust. Lambda: $0.20 pro Million Invocations. DynamoDB: $0.25 pro Million Write Units. Klingt günstig. Ist es auch.

Was nicht alle zeigen: die Services um deinen Service herum. NAT Gateway, Data Transfer, CloudWatch Logs, API Gateway, EBS Snapshots. Die stehen nicht im Architekturdiagramm. Die stehen auf deiner Rechnung.

Klick auf die einzelnen Kostenfallen und schau was sie tatsächlich kosten und wie du sie fixst:

VERSTECKTE KOSTEN
$2,016/mo
EINSPARPOTENZIAL
$1,376/mo

$2.016 pro Monat. Versteckt. Davon $1.376 einsparbar. Ohne einen einzigen Service zu ändern.

NAT Gateway: der stille Killer

$32 pro Monat. Dafür dass er existiert. Pro AZ. Plus $0.045 pro GB Traffic. Drei AZs für High Availability? $96 Grundkosten bevor ein einziges Byte fließt.

Warum brauchst du den? Weil deine Lambda in einer VPC sitzt und ins Internet will. Oder zu einem AWS Service wie DynamoDB.

Seit 2019 kann Lambda ohne VPC auf die meisten AWS Services zugreifen. Wenn dein Lambda nur DynamoDB und S3 nutzt: raus aus der VPC. NAT Gateway gespart. Wenn du eine RDS brauchst: VPC Endpoints für AWS Services kosten $7/mo statt $32/mo für den NAT Gateway.

Data Transfer: der unsichtbare Posten

$0.01 pro GB zwischen AZs. Klingt nach nichts. Rechne mal: drei Microservices die sich 1.000 mal pro Sekunde aufrufen, 2KB pro Request. Das sind 86 GB pro Tag. $26 pro Monat nur für interne Kommunikation. Für drei Services.

Bei 20 Services? $180 und mehr. Und das steht nirgends in deinem Architekturdiagramm.

// ECS: Availability Zone aus den Metadata lesen
const az = await fetch(
  "http://169.254.169.254/latest/meta-data/placement/availability-zone",
).then((r) => r.text());

// Requests bevorzugt an Services in derselben AZ routen
function getServiceUrl(serviceName: string): string {
  const endpoints = serviceDiscovery.get(serviceName);
  const sameAZ = endpoints.filter((e) => e.az === az);
  return sameAZ.length > 0
    ? sameAZ[Math.floor(Math.random() * sameAZ.length)].url
    : endpoints[Math.floor(Math.random() * endpoints.length)].url;
}

AZ-Aware Routing reduziert Cross-AZ Traffic um 60-80%. In EKS gibt’s dafür Topology Aware Hints: ein Annotation auf dem Service und Kubernetes routet automatisch in der gleichen AZ.

CloudWatch Logs: der heimliche Speicherfresser

$0.50 pro GB Ingestion. Klingt fair. Bis du merkst dass dein DEBUG-Logging in Produktion 30 GB pro Tag produziert. $450 pro Monat. Für Logs die niemand liest.

Und die bleiben für immer. Default Retention: Never Expire. Nach einem Jahr hast du 11 TB Logs. $330 pro Monat nur fürs Speichern.

const LOG_LEVEL = process.env.LOG_LEVEL || "warn";

const LEVELS = { debug: 0, info: 1, warn: 2, error: 3 };

function log(level: keyof typeof LEVELS, msg: string, data?: unknown) {
  if (LEVELS[level] < LEVELS[LOG_LEVEL as keyof typeof LEVELS]) return;
  console.log(JSON.stringify({ level, msg, data, ts: Date.now() }));
}

Drei Dinge die sofort helfen:

  1. Log Level WARN in Produktion. DEBUG und INFO nur bei aktivem Debugging.
  2. Retention auf 14 Tage. Alles älter als 2 Wochen brauchst du nicht in CloudWatch.
  3. S3 Export für Langzeit-Archivierung. S3 Standard-IA kostet $0.0125/GB, 2.4x billiger als CloudWatch.

AWS bietet “CloudWatch Logs Insights” für $0.005 pro GB gescannt. Klingt billig bis du 10 TB Logs hast und eine Query $50 kostet. Für ernsthafte Log-Analyse: exportier nach S3, query mit Athena.

EBS: das vergessene Volume

GP2 auf GP3 migrieren kostet dich nichts und spart 20%. Und GP3 ist schneller: 3.000 IOPS inklusive statt 100 IOPS/GB bei GP2.

Aber der echte Kostenfresser: vergessene Snapshots. Du löschst eine EC2 Instanz, die Snapshots bleiben. Du löschst ein EBS Volume, die Snapshots bleiben. Nach einem Jahr hast du Snapshots von Instanzen die längst nicht mehr existieren.

RDS: Right-Sizing

Die Faustregel: wenn deine CPU-Auslastung unter 20% liegt, ist deine Instanz zu groß. Und bei den meisten Teams: sie ist zu groß.

db.r6g.xlarge hat 4 vCPUs und 32 GB RAM. Kostet $400/mo. Die meisten Datenbanken brauchen db.r6g.large (2 vCPU, 16 GB) für $200/mo. Multi-AZ verdoppelt beides.

Reserved Instances: 30-40% Rabatt wenn du für 1 Jahr committed. Savings Plans: flexibler, gleicher Rabatt. Wenn du weißt dass deine RDS die nächsten 12 Monate läuft (und das tut sie), gibt es keinen Grund On-Demand zu zahlen.

Monatliches Cost Review

Ernsthaft: setz dir einen monatlichen Termin. 30 Minuten. Geh durch AWS Cost Explorer, sortiert nach Service. Such nach:

Die $1.376 Einsparung aus der Visualisation oben? Findet man in einer halben Stunde. Wenn man hinschaut.