Cloud Cost Optimization
Cloud Cost Optimization
Cloud-Kosten können schnell explodieren ohne aktives Management. Lernen Sie Strategien und Tools zur Kostenoptimierung in AWS, GCP und Azure.
Kostenverteilung verstehen
┌─────────────────────────────────────────────────────────────┐ │ TYPISCHE CLOUD-KOSTEN │ ├─────────────────────────────────────────────────────────────┤ │ │ │ ┌─────────────────────────────────────────────┐ │ │ │ │ │ │ │ COMPUTE ████████████████████ 45% │ │ │ │ (EC2, VMs, Kubernetes) │ │ │ │ │ │ │ │ STORAGE ██████████████ 25% │ │ │ │ (S3, EBS, Databases) │ │ │ │ │ │ │ │ DATA TRANSFER █████████ 15% │ │ │ │ (Egress, CDN) │ │ │ │ │ │ │ │ OTHER ███████ 15% │ │ │ │ (Managed Services, Support) │ │ │ │ │ │ │ └─────────────────────────────────────────────┘ │ │ │ │ Größte Einsparpotenziale: Compute und Storage │ │ │ └─────────────────────────────────────────────────────────────┘
Right-Sizing
PROBLEM: Überdimensionierte Instanzen ┌─────────────────────────────────────────────────────────────┐ │ Instance: m5.2xlarge │ │ Kosten: $280/Monat │ │ │ │ CPU Nutzung: ████░░░░░░░░░░░░░░░░ 20% │ │ Memory: ██████░░░░░░░░░░░░░░ 30% │ │ │ │ → 70-80% der Ressourcen werden verschwendet! │ └─────────────────────────────────────────────────────────────┘ LÖSUNG: Right-Sizing auf m5.large → Ersparnis: ~$200/Monat pro Instanz
# AWS: Compute Optimizer Empfehlungen aws compute-optimizer get-ec2-instance-recommendations \ --filters name=Finding,values=Overprovisioned # AWS CloudWatch: CPU-Auslastung analysieren aws cloudwatch get-metric-statistics \ --namespace AWS/EC2 \ --metric-name CPUUtilization \ --dimensions Name=InstanceId,Value=i-1234567890abcdef0 \ --start-time 2024-01-01T00:00:00Z \ --end-time 2024-01-31T23:59:59Z \ --period 86400 \ --statistics Average Maximum # GCP: Rightsizing Recommendations gcloud recommender recommendations list \ --project=my-project \ --location=us-central1 \ --recommender=google.compute.instance.MachineTypeRecommender # Kubernetes: Vertical Pod Autoscaler Recommendations kubectl describe vpa myapp-vpa
Reserved Instances & Savings Plans
PREISMODELLE VERGLEICH ┌─────────────┬────────────────┬────────────────┬────────────────┐ │ Modell │ Flexibilität │ Ersparnis │ Commitment │ ├─────────────┼────────────────┼────────────────┼────────────────┤ │ On-Demand │ Maximal │ 0% │ Keins │ ├─────────────┼────────────────┼────────────────┼────────────────┤ │ Savings Plan│ Hoch │ bis 72% │ 1-3 Jahre │ │ (AWS) │ (Jede Instanz) │ │ │ ├─────────────┼────────────────┼────────────────┼────────────────┤ │ Reserved │ Gering │ bis 75% │ 1-3 Jahre │ │ Instances │ (Fix Instance) │ │ │ ├─────────────┼────────────────┼────────────────┼────────────────┤ │ Spot/ │ Gering │ bis 90% │ Keins │ │ Preemptible │ (Unterbrechbar)│ │ │ └─────────────┴────────────────┴────────────────┴────────────────┘ Empfehlung: - Baseline Workload → Reserved/Savings Plan - Variable Workload → On-Demand - Fault-tolerant Jobs → Spot Instances
# AWS Savings Plan kaufen aws savingsplans create-savings-plan \ --savings-plan-offering-id sp-offering-123 \ --commitment 100.0 \ --savings-plan-type ComputeSavingsPlans \ --term 1year \ --payment-option AllUpfront # GCP Committed Use Discounts gcloud compute commitments create my-commitment \ --region=us-central1 \ --plan=12-month \ --resources=vcpu=100,memory=400GB # Azure Reserved Instances az reservations reservation-order purchase \ --sku Standard_D2s_v3 \ --location eastus \ --term P1Y \ --quantity 10
Spot/Preemptible Instances
# AWS Spot Instance Request
aws ec2 request-spot-instances \
--instance-count 5 \
--type persistent \
--launch-specification file://spot-spec.json
# spot-spec.json
{
"ImageId": "ami-12345678",
"InstanceType": "m5.large",
"KeyName": "my-key",
"SecurityGroupIds": ["sg-12345678"]
}
# Kubernetes mit Spot Nodes (Karpenter)
apiVersion: karpenter.sh/v1alpha5
kind: Provisioner
metadata:
name: spot-provisioner
spec:
requirements:
- key: karpenter.sh/capacity-type
operator: In
values: ["spot"]
- key: node.kubernetes.io/instance-type
operator: In
values: ["m5.large", "m5.xlarge", "m5a.large"]
limits:
resources:
cpu: 1000
provider:
subnetSelector:
karpenter.sh/discovery: my-cluster
Auto Scaling
# AWS Auto Scaling Group
aws autoscaling create-auto-scaling-group \
--auto-scaling-group-name my-asg \
--min-size 2 \
--max-size 20 \
--desired-capacity 4 \
--launch-template LaunchTemplateId=lt-12345
# Target Tracking Policy
aws autoscaling put-scaling-policy \
--auto-scaling-group-name my-asg \
--policy-name cpu-target-tracking \
--policy-type TargetTrackingScaling \
--target-tracking-configuration '{
"TargetValue": 70.0,
"PredefinedMetricSpecification": {
"PredefinedMetricType": "ASGAverageCPUUtilization"
},
"ScaleInCooldown": 300,
"ScaleOutCooldown": 60
}'
# Kubernetes HPA
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
name: myapp-hpa
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: myapp
minReplicas: 2
maxReplicas: 20
metrics:
- type: Resource
resource:
name: cpu
target:
type: Utilization
averageUtilization: 70
Scheduled Scaling
# Non-Production Umgebungen nachts/Wochenende herunterfahren
# AWS: Scheduled Actions
aws autoscaling put-scheduled-action \
--auto-scaling-group-name dev-asg \
--scheduled-action-name scale-down-night \
--recurrence "0 19 * * MON-FRI" \
--desired-capacity 0
aws autoscaling put-scheduled-action \
--auto-scaling-group-name dev-asg \
--scheduled-action-name scale-up-morning \
--recurrence "0 7 * * MON-FRI" \
--desired-capacity 3
# Kubernetes: KEDA ScaledObject mit Cron
apiVersion: keda.sh/v1alpha1
kind: ScaledObject
metadata:
name: cron-scaler
spec:
scaleTargetRef:
name: myapp
minReplicaCount: 0
maxReplicaCount: 10
triggers:
- type: cron
metadata:
timezone: Europe/Berlin
start: "0 7 * * MON-FRI"
end: "0 19 * * MON-FRI"
desiredReplicas: "5"
Storage Optimization
# S3 Intelligent Tiering (automatisch)
aws s3api put-bucket-intelligent-tiering-configuration \
--bucket my-bucket \
--id my-config \
--intelligent-tiering-configuration '{
"Status": "Enabled",
"Tierings": [
{"Days": 90, "AccessTier": "ARCHIVE_ACCESS"},
{"Days": 180, "AccessTier": "DEEP_ARCHIVE_ACCESS"}
]
}'
# S3 Lifecycle Rules
aws s3api put-bucket-lifecycle-configuration \
--bucket my-bucket \
--lifecycle-configuration '{
"Rules": [
{
"ID": "MoveToGlacier",
"Status": "Enabled",
"Filter": {"Prefix": "logs/"},
"Transitions": [
{"Days": 30, "StorageClass": "GLACIER"},
{"Days": 365, "StorageClass": "DEEP_ARCHIVE"}
],
"Expiration": {"Days": 730}
}
]
}'
# EBS: Ungenutzte Volumes finden
aws ec2 describe-volumes \
--filters Name=status,Values=available \
--query 'Volumes[*].[VolumeId,Size,CreateTime]'
Data Transfer Kosten
DATA TRANSFER PREISE (Beispiel AWS) ┌────────────────────────┬─────────────────────────────────┐ │ Transfer Typ │ Kosten │ ├────────────────────────┼─────────────────────────────────┤ │ Ingress (Upload) │ KOSTENLOS │ ├────────────────────────┼─────────────────────────────────┤ │ Same Region, Same AZ │ KOSTENLOS │ ├────────────────────────┼─────────────────────────────────┤ │ Same Region, Cross-AZ │ ~$0.01/GB │ ├────────────────────────┼─────────────────────────────────┤ │ Egress (Download) │ $0.05-0.09/GB │ ├────────────────────────┼─────────────────────────────────┤ │ Cross-Region │ $0.02/GB │ └────────────────────────┴─────────────────────────────────┘ OPTIMIERUNGEN: • CDN für statische Inhalte (CloudFront: $0.085/GB) • Komprimierung aktivieren • Services in gleicher AZ platzieren • VPC Endpoints statt Internet Gateway
Kosten-Monitoring
# AWS Cost Explorer CLI
aws ce get-cost-and-usage \
--time-period Start=2024-01-01,End=2024-01-31 \
--granularity DAILY \
--metrics "BlendedCost" \
--group-by Type=DIMENSION,Key=SERVICE
# Budget Alert erstellen
aws budgets create-budget \
--account-id 123456789012 \
--budget '{
"BudgetName": "Monthly-Limit",
"BudgetLimit": {"Amount": "1000", "Unit": "USD"},
"BudgetType": "COST",
"TimeUnit": "MONTHLY"
}' \
--notifications-with-subscribers '[
{
"Notification": {
"NotificationType": "ACTUAL",
"ComparisonOperator": "GREATER_THAN",
"Threshold": 80,
"ThresholdType": "PERCENTAGE"
},
"Subscribers": [
{"SubscriptionType": "EMAIL", "Address": "finance@example.com"}
]
}
]'
# Kubernetes: Kubecost für Cluster-Kosten
helm install kubecost kubecost/cost-analyzer \
--namespace kubecost \
--create-namespace
Tagging Strategy
# Ressourcen taggen für Kostenaufteilung
PFLICHT-TAGS:
- Environment: production, staging, development
- Team: platform, frontend, backend
- Project: project-name
- CostCenter: CC-12345
# AWS: Tag Policy
{
"tags": {
"Environment": {
"tag_key": "Environment",
"tag_value": ["production", "staging", "development"],
"enforced_for": ["ec2:instance", "rds:db"]
},
"Team": {
"tag_key": "Team",
"enforced_for": ["*"]
}
}
}
# Terraform: Default Tags
provider "aws" {
default_tags {
tags = {
Environment = var.environment
Team = var.team
ManagedBy = "terraform"
}
}
}
Quick Wins Checkliste
SOFORT UMSETZBAR (1-2 Wochen)
[ ] Ungenutzte Ressourcen identifizieren und löschen
- Unattached EBS Volumes
- Alte Snapshots
- Unused Elastic IPs
- Leere S3 Buckets
[ ] Dev/Test Environments nachts/Wochenende stoppen
[ ] Right-Sizing für überdimensionierte Instanzen
MITTELFRISTIG (1-3 Monate)
[ ] Savings Plans/Reserved Instances für Baseline
[ ] Spot Instances für fault-tolerant Workloads
[ ] S3 Lifecycle Policies
[ ] CDN für statische Inhalte
LANGFRISTIG (3-6 Monate)
[ ] Tagging Strategy implementieren
[ ] FinOps Prozesse etablieren
[ ] Architektur-Review für Kosteneffizienz
[ ] Automated Cost Anomaly Detection
💡 Best Practices:
1. Kosten-Monitoring von Tag 1 einrichten
2. Budget-Alerts vor Überraschungen
3. Tagging für Kostenaufteilung
4. Regelmäßige Right-Sizing Reviews
5. FinOps als Team-Verantwortung etablieren
2. Budget-Alerts vor Überraschungen
3. Tagging für Kostenaufteilung
4. Regelmäßige Right-Sizing Reviews
5. FinOps als Team-Verantwortung etablieren