Zum Inhalt springen

CDKTF Cheat Sheet

Overview

CDKTF (Cloud Development Kit for Terraform) allows developers to define infrastructure using familiar programming languages like TypeScript, Python, Go, Java, and C# instead of HashiCorp Configuration Language (HCL). It synthesizes standard Terraform JSON configuration, leveraging the full Terraform ecosystem of providers and modules while offering the benefits of general-purpose programming languages.

CDKTF provides constructs that map to Terraform resources, data sources, and modules. Developers can use loops, conditionals, functions, classes, and other language features to create reusable infrastructure patterns. The tool integrates with the Terraform CLI for planning and applying changes.

Installation

# Install via npm (requires Node.js)
npm install -g cdktf-cli

# Verify
cdktf --version

# Prerequisites: Terraform CLI
brew install terraform  # macOS
# or
sudo apt install terraform  # Linux

Core Commands

CommandDescription
cdktf initInitialize a new CDKTF project
cdktf synthSynthesize Terraform configuration
cdktf planPlan infrastructure changes
cdktf deployApply infrastructure changes
cdktf destroyDestroy infrastructure
cdktf diffShow diff of changes
cdktf outputShow stack outputs
cdktf provider addAdd a Terraform provider
cdktf getGenerate provider bindings
cdktf convertConvert HCL to CDKTF code

Project Setup

Initialize Project

# Interactive init
cdktf init

# TypeScript project
cdktf init --template=typescript --local

# Python project
cdktf init --template=python --local

# Go project
cdktf init --template=go --local

# Add providers
cdktf provider add aws
cdktf provider add google
cdktf provider add azurerm

# Generate provider bindings
cdktf get

TypeScript Usage

Basic Infrastructure

import { Construct } from 'constructs';
import { App, TerraformStack, TerraformOutput } from 'cdktf';
import { AwsProvider } from '@cdktf/provider-aws/lib/provider';
import { Instance } from '@cdktf/provider-aws/lib/instance';
import { Vpc } from '@cdktf/provider-aws/lib/vpc';
import { Subnet } from '@cdktf/provider-aws/lib/subnet';

class MyStack extends TerraformStack {
  constructor(scope: Construct, id: string) {
    super(scope, id);

    new AwsProvider(this, 'AWS', { region: 'us-east-1' });

    const vpc = new Vpc(this, 'vpc', {
      cidrBlock: '10.0.0.0/16',
      tags: { Name: 'my-vpc' },
    });

    const subnet = new Subnet(this, 'subnet', {
      vpcId: vpc.id,
      cidrBlock: '10.0.1.0/24',
      availabilityZone: 'us-east-1a',
    });

    const instance = new Instance(this, 'web', {
      ami: 'ami-0c55b159cbfafe1f0',
      instanceType: 't3.micro',
      subnetId: subnet.id,
      tags: { Name: 'web-server' },
    });

    new TerraformOutput(this, 'public_ip', {
      value: instance.publicIp,
    });
  }
}

const app = new App();
new MyStack(app, 'my-infrastructure');
app.synth();

Reusable Constructs

import { Construct } from 'constructs';
import { S3Bucket } from '@cdktf/provider-aws/lib/s3-bucket';
import { S3BucketVersioningA } from '@cdktf/provider-aws/lib/s3-bucket-versioning';

class SecureBucket extends Construct {
  public readonly bucket: S3Bucket;

  constructor(scope: Construct, id: string, props: { name: string }) {
    super(scope, id);

    this.bucket = new S3Bucket(this, 'bucket', {
      bucket: props.name,
      tags: { ManagedBy: 'cdktf' },
    });

    new S3BucketVersioningA(this, 'versioning', {
      bucket: this.bucket.id,
      versioningConfiguration: { status: 'Enabled' },
    });
  }
}

Python Usage

from constructs import Construct
from cdktf import App, TerraformStack, TerraformOutput
from cdktf_cdktf_provider_aws.provider import AwsProvider
from cdktf_cdktf_provider_aws.instance import Instance
from cdktf_cdktf_provider_aws.vpc import Vpc

class MyStack(TerraformStack):
    def __init__(self, scope: Construct, id: str):
        super().__init__(scope, id)

        AwsProvider(self, "AWS", region="us-east-1")

        vpc = Vpc(self, "vpc",
            cidr_block="10.0.0.0/16",
            tags={"Name": "my-vpc"})

        instance = Instance(self, "web",
            ami="ami-0c55b159cbfafe1f0",
            instance_type="t3.micro",
            tags={"Name": "web-server"})

        TerraformOutput(self, "public_ip",
            value=instance.public_ip)

app = App()
MyStack(app, "my-infrastructure")
app.synth()

Configuration

cdktf.json

{
  "language": "typescript",
  "app": "npx ts-node main.ts",
  "projectId": "abc123",
  "sendCrashReports": false,
  "terraformProviders": [
    "hashicorp/aws@~> 5.0",
    "hashicorp/google@~> 5.0"
  ],
  "terraformModules": [
    {
      "name": "vpc",
      "source": "terraform-aws-modules/vpc/aws",
      "version": "5.4.0"
    }
  ],
  "context": {
    "excludeStackIdFromLogicalIds": true
  }
}

Multiple Stacks

const app = new App();

new NetworkStack(app, 'network');
new DatabaseStack(app, 'database');
new AppStack(app, 'application');

app.synth();
# Deploy specific stack
cdktf deploy network
cdktf deploy database application

# Deploy all
cdktf deploy '*'

Advanced Usage

Using Terraform Modules

import { TerraformHclModule } from 'cdktf';

new TerraformHclModule(this, 'vpc', {
  source: 'terraform-aws-modules/vpc/aws',
  version: '5.4.0',
  variables: {
    name: 'my-vpc',
    cidr: '10.0.0.0/16',
    azs: ['us-east-1a', 'us-east-1b'],
    private_subnets: ['10.0.1.0/24', '10.0.2.0/24'],
    public_subnets: ['10.0.101.0/24', '10.0.102.0/24'],
    enable_nat_gateway: true,
  },
});

Remote State Backend

import { S3Backend } from 'cdktf';

new S3Backend(this, {
  bucket: 'my-terraform-state',
  key: 'cdktf/terraform.tfstate',
  region: 'us-east-1',
  dynamodbTable: 'terraform-locks',
  encrypt: true,
});

Convert HCL to CDKTF

# Convert existing HCL to TypeScript
cdktf convert --language typescript < main.tf

# Convert to Python
cdktf convert --language python < main.tf

Iterators and Loops

import { TerraformIterator } from 'cdktf';

const environments = ['dev', 'staging', 'prod'];

const iterator = TerraformIterator.fromList(environments);

new S3Bucket(this, 'buckets', {
  forEach: iterator,
  bucket: `my-app-${iterator.value}`,
  tags: { Environment: iterator.value },
});

Troubleshooting

IssueSolution
Provider bindings not foundRun cdktf get after adding providers
Synth failsCheck TypeScript/Python syntax; run cdktf synth --debug
State conflictConfigure remote backend before deploying
Import not resolvingCheck cdktf.json provider versions
Circular dependencyRestructure stacks; use cross-stack references
Deploy timeoutCheck Terraform provider for slow resources
# Debug synthesis
cdktf synth --debug

# View generated Terraform JSON
cat cdktf.out/stacks/my-stack/cdk.tf.json | jq .

# Plan without deploying
cdktf plan

# Show outputs
cdktf output

# Destroy infrastructure
cdktf destroy