Use Cases (Aktualisiert: 3.6.2026)

Claude Code mit AWS CloudFormation und CDK: Praxisleitfaden für IaC-Reviews

AWS CDK und CloudFormation mit Claude Code prüfen: Least-Privilege-IAM, Diffs, Drift, Rollback und Guardrails.

Claude Code mit AWS CloudFormation und CDK: Praxisleitfaden für IaC-Reviews

Ein paar Klicks in der AWS-Konsole wirken schnell, bis jemand fragt, warum Produktion anders aussieht als Staging. CloudFormation und AWS CDK bringen Infrastruktur in Code, aber IaC ist nicht automatisch sicher. Eine zu breite IAM-Policy, ein unbeabsichtigter Austausch einer Stateful Resource oder ein vergessener NAT Gateway können Sicherheits- und Kostenprobleme auslösen.

Ich nutze Claude Code deshalb als Entwurfs- und Review-Partner, nicht als autonomen Deployment-Operator. Claude Code kann CloudFormation/CDK-Entwürfe erstellen, cdk diff erklären, IAM-Erweiterungen markieren und CloudFormation-Events in eine Rollback-Checkliste übersetzen. Die Freigabe bleibt menschlich.

Kurz für Einsteiger: CloudFormation ist der AWS-Service, der Templates ausführt. CDK beschreibt Infrastruktur in TypeScript und synthetisiert daraus CloudFormation. Ein Stack ist die deploybare Einheit. Drift bedeutet, dass die echte AWS-Ressource nicht mehr zum Code passt.

Dieser Artikel folgt den offiziellen AWS-Dokumenten, geprüft am 3. Juni 2026:

Grenzen festlegen

AufgabeClaude Code hilft beiMensch prüft
AnforderungenRessourcen, Umgebungen, AbhängigkeitenOb die Ressource nötig ist
EntwurfCloudFormation/CDK-CodeNamen, Löschung, Kosten
IAMKandidaten für Action/Resource/ConditionLeast Privilege
DiffErklärung von cdk diff oder change setDeletes, Replacements, Rechte
StörungEvent-Analyse, Fix-IdeenRollback-Plan
flowchart LR
  A["Anforderungen schreiben"] --> B["IaC-Entwurf mit Claude Code"]
  B --> C["Kosten und Namen prüfen"]
  C --> D["cdk diff oder change set"]
  D --> E["Risiko-Review mit Claude Code"]
  E --> F["Freigeben und deployen"]
  F --> G["Drift und Rollback dokumentieren"]

Use Case 1: Kleine Umgebung nach CloudFormation übertragen

Beginnen Sie mit einem risikoarmen Ausschnitt. Dieses Template erstellt einen privaten S3-Bucket und eine Lambda-assumierbare IAM-Rolle, die nur diesen Bucket lesen darf. Da eine benannte IAM-Rolle erstellt wird, ist CAPABILITY_NAMED_IAM nötig.

mkdir cfn-iac-review-demo
cd cfn-iac-review-demo
# Das folgende YAML als cfn-safe-iac-demo.yaml speichern
AWSTemplateFormatVersion: "2010-09-09"
Description: "ClaudeCodeLab safe IaC review demo: private S3 bucket and least-privilege Lambda role"

Parameters:
  Environment:
    Type: String
    Default: dev
    AllowedValues:
      - dev
      - staging
      - prod
  ProjectName:
    Type: String
    Default: cclab-iac-demo
    AllowedPattern: "^[a-z0-9][a-z0-9-]{2,24}$"

Resources:
  DemoBucket:
    Type: AWS::S3::Bucket
    DeletionPolicy: Retain
    UpdateReplacePolicy: Retain
    Properties:
      BucketName: !Sub "${ProjectName}-${Environment}-${AWS::AccountId}-${AWS::Region}"
      VersioningConfiguration:
        Status: Enabled
      PublicAccessBlockConfiguration:
        BlockPublicAcls: true
        BlockPublicPolicy: true
        IgnorePublicAcls: true
        RestrictPublicBuckets: true
      BucketEncryption:
        ServerSideEncryptionConfiguration:
          - ServerSideEncryptionByDefault:
              SSEAlgorithm: AES256
      Tags:
        - Key: Project
          Value: !Ref ProjectName
        - Key: Environment
          Value: !Ref Environment

  DemoReaderRole:
    Type: AWS::IAM::Role
    Properties:
      RoleName: !Sub "${ProjectName}-${Environment}-reader-${AWS::Region}"
      AssumeRolePolicyDocument:
        Version: "2012-10-17"
        Statement:
          - Effect: Allow
            Principal:
              Service: lambda.amazonaws.com
            Action: sts:AssumeRole
      Policies:
        - PolicyName: ReadOnlyDemoBucket
          PolicyDocument:
            Version: "2012-10-17"
            Statement:
              - Sid: ListOnlyThisBucket
                Effect: Allow
                Action:
                  - s3:ListBucket
                Resource: !GetAtt DemoBucket.Arn
              - Sid: ReadObjectsOnly
                Effect: Allow
                Action:
                  - s3:GetObject
                Resource: !Sub "${DemoBucket.Arn}/*"

Outputs:
  BucketName:
    Value: !Ref DemoBucket
  ReaderRoleArn:
    Value: !GetAtt DemoReaderRole.Arn

Vorher streng prüfen lassen:

claude -p "
Prüfe cfn-safe-iac-demo.yaml als CloudFormation-Template.
Gib eine Tabelle aus zu:
1. versehentlicher öffentlicher Zugriff
2. IAM Resource Scope
3. Lösch- oder Ersatzrisiko
4. mögliche Monatskosten
5. Punkte im Produktions-change-set
"

Dann change set erstellen und ansehen:

aws cloudformation create-change-set \
  --stack-name cclab-iac-demo-dev \
  --change-set-name review-20260603-001 \
  --template-body file://cfn-safe-iac-demo.yaml \
  --capabilities CAPABILITY_NAMED_IAM \
  --parameters ParameterKey=Environment,ParameterValue=dev ParameterKey=ProjectName,ParameterValue=cclab-iac-demo

aws cloudformation describe-change-set \
  --stack-name cclab-iac-demo-dev \
  --change-set-name review-20260603-001

Achten Sie auf Add, Modify, Remove und Replacement. Ein Replacement bei S3, RDS, DynamoDB, KMS oder Netzwerkressourcen braucht eine bewusste Freigabe.

Use Case 2: Minimaler CDK-TypeScript-Stack

Für neue Projekte ist CDK TypeScript gut prüfbar. Dieses Beispiel nutzt DynamoDB, S3 und Lambda, aber kein API Gateway, damit die Testfläche klein bleibt.

mkdir cdk-iac-review-demo
cd cdk-iac-review-demo
npm init -y
npm install aws-cdk-lib constructs
npm install --save-dev aws-cdk typescript ts-node @types/node
mkdir bin lib
{
  "app": "npx ts-node --prefer-ts-exts bin/app.ts"
}
// bin/app.ts
import * as cdk from "aws-cdk-lib";
import { IacReviewDemoStack } from "../lib/iac-review-demo-stack";

const app = new cdk.App();

new IacReviewDemoStack(app, "IacReviewDemoStack", {
  env: {
    account: process.env.CDK_DEFAULT_ACCOUNT,
    region: process.env.CDK_DEFAULT_REGION ?? "eu-central-1",
  },
});
// lib/iac-review-demo-stack.ts
import * as cdk from "aws-cdk-lib";
import { Construct } from "constructs";
import * as dynamodb from "aws-cdk-lib/aws-dynamodb";
import * as iam from "aws-cdk-lib/aws-iam";
import * as lambda from "aws-cdk-lib/aws-lambda";
import * as logs from "aws-cdk-lib/aws-logs";
import * as s3 from "aws-cdk-lib/aws-s3";

export class IacReviewDemoStack extends cdk.Stack {
  constructor(scope: Construct, id: string, props?: cdk.StackProps) {
    super(scope, id, props);

    const stage = this.node.tryGetContext("stage") ?? "dev";
    const isProd = stage === "prod";

    const table = new dynamodb.Table(this, "AppTable", {
      partitionKey: { name: "pk", type: dynamodb.AttributeType.STRING },
      billingMode: dynamodb.BillingMode.PAY_PER_REQUEST,
      pointInTimeRecovery: isProd,
      deletionProtection: isProd,
      removalPolicy: isProd ? cdk.RemovalPolicy.RETAIN : cdk.RemovalPolicy.DESTROY,
    });

    const bucket = new s3.Bucket(this, "PrivateAssetsBucket", {
      blockPublicAccess: s3.BlockPublicAccess.BLOCK_ALL,
      enforceSSL: true,
      encryption: s3.BucketEncryption.S3_MANAGED,
      versioned: true,
      removalPolicy: isProd ? cdk.RemovalPolicy.RETAIN : cdk.RemovalPolicy.DESTROY,
      autoDeleteObjects: !isProd,
    });

    const fn = new lambda.Function(this, "ApiHandler", {
      runtime: lambda.Runtime.NODEJS_20_X,
      handler: "index.handler",
      code: lambda.Code.fromInline(`
exports.handler = async () => ({
  statusCode: 200,
  body: JSON.stringify({
    tableName: process.env.TABLE_NAME,
    bucketName: process.env.BUCKET_NAME
  })
});
`),
      environment: {
        TABLE_NAME: table.tableName,
        BUCKET_NAME: bucket.bucketName,
        STAGE: stage,
      },
      timeout: cdk.Duration.seconds(10),
      memorySize: 256,
      logRetention: logs.RetentionDays.ONE_WEEK,
    });

    table.grantReadWriteData(fn);
    bucket.grantPut(fn);

    fn.addToRolePolicy(
      new iam.PolicyStatement({
        sid: "DenyInsecureS3Transport",
        effect: iam.Effect.DENY,
        actions: ["s3:*"],
        resources: [bucket.bucketArn, bucket.arnForObjects("*")],
        conditions: { Bool: { "aws:SecureTransport": "false" } },
      }),
    );

    cdk.Tags.of(this).add("Project", "ClaudeCodeLab");
    cdk.Tags.of(this).add("Stage", stage);

    new cdk.CfnOutput(this, "FunctionName", { value: fn.functionName });
    new cdk.CfnOutput(this, "BucketName", { value: bucket.bucketName });
    new cdk.CfnOutput(this, "TableName", { value: table.tableName });
  }
}

Vor dem Deploy:

npx cdk synth -c stage=dev
npx cdk diff -c stage=dev
claude -p "
Prüfe diesen cdk diff.
Markiere nur Deletes, Replacements, IAM-Erweiterungen, S3-Exposition, DynamoDB-Kosten und Lambda-Env-Leaks.
$(npx cdk diff -c stage=dev 2>&1)
"

autoDeleteObjects: !isProd ist in Entwicklung bequem, aber in Produktion gefährlich. Genau solche Guardrails soll Claude Code herausarbeiten.

Use Case 3: Produktions-Diffs erklären

claude -p "
Fasse diesen cdk diff für eine Produktverantwortliche ohne AWS-Spezialwissen zusammen.
Spalten:
- Änderungstyp
- Zielressource
- Nutzerwirkung
- Sicherheitswirkung
- Kostenwirkung
- Frage vor Freigabe

$(npx cdk diff -c stage=prod 2>&1)
"

Typische Risiken sind IAM Action/Resource, Security Groups mit 0.0.0.0/0, fehlender Löschschutz, öffentlicher S3-Zugriff, neue CloudFront/NAT-Gateway-Ressourcen und Stateful Replacements.

Use Case 4: Rollback und Drift

aws cloudformation describe-stacks --stack-name cclab-iac-demo-dev
aws cloudformation detect-stack-drift --stack-name cclab-iac-demo-dev
aws cloudformation describe-stack-drift-detection-status --stack-drift-detection-id YOUR_DETECTION_ID
claude -p "
Dieser Stack ist in UPDATE_ROLLBACK_FAILED.
Lies die Events und trenne wahrscheinliche Ursachen, berührbare Ressourcen, nicht berührbare Ressourcen und Schritte aus AWS-Dokumentation.
$(aws cloudformation describe-stack-events --stack-name cclab-iac-demo-dev 2>&1)
"

Häufige Fallstricke

Zu breites IAM. Akzeptieren Sie nicht Action: "*" oder Resource: "*", nur weil es funktioniert. Actions, ARNs und Conditions müssen zum Use Case passen.

Deploy ohne Diff. Vor Produktion gehören synth, diff und change set dazu. Bei Replacement wird gestoppt.

Fixkosten übersehen. ALB, NAT Gateway, RDS, OpenSearch und dauerhaft laufende ECS-Services kosten auch bei wenig Traffic.

Konsolenänderung als Dauerlösung. Manuelle Eingriffe können im Incident nötig sein, müssen aber zurück in CloudFormation oder CDK.

Secrets im Code. Nutzen Sie Secrets Manager oder SSM Parameter Store und weisen Sie Claude Code an, keine geheimen Werte auszugeben.

Review-Prompt

Du bist ein strenger AWS CloudFormation/CDK Reviewer.
Prüfe diesen IaC-Diff vor Produktion.

Prüfen:
- IAM Action/Resource/Condition nach Least Privilege
- versehentliche Öffnung über Security Groups oder S3
- Delete oder Replacement von Stateful Resources
- neue Fixkosten wie ALB, NAT Gateway, RDS oder OpenSearch
- wahrscheinlicher CloudFormation Drift
- Ressourcen mit manuellen Rollback-Schritten

Ausgabe:
1. jetzt zu korrigierende Probleme
2. Fragen für die Freigabe
3. Befehle vor deploy
4. Befehle nach deploy

Mehr erfahren

Für IAM-Details lesen Sie Claude Code und AWS IAM. Ergänzend passen AWS Lambda, AWS API Gateway und AWS DynamoDB.

ClaudeCodeLab bietet Praxisprodukte und Team-Training, um diese Prompts in Pull-Request-Vorlagen und Release-Checklisten zu übersetzen.

Fazit

Claude Code ist mit CloudFormation/CDK am wertvollsten als strenger zweiter Reviewer. Lassen Sie es entwerfen, aber verlangen Sie vor dem Deploy eine Erklärung zu IAM, Kosten, Replacements, Rollback und Drift. Praktisch findet das Review von cdk diff und change sets mehr Produktionsrisiken als reine Template-Generierung.

#claude-code #aws #cloudformation #cdk #iac #typescript
Kostenlos

Kostenloses PDF: Claude-Code-Cheatsheet

E-Mail eintragen und eine Seite mit Befehlen, Review-Gewohnheiten und sicheren Workflows herunterladen.

Wir schützen Ihre Daten und senden keinen Spam.

Masa

Über den Autor

Masa

Engineer für praktische Claude-Code-Workflows und Team-Einführung.