> ## Documentation Index
> Fetch the complete documentation index at: https://cdktn.io/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Configuration - CDK Terrain

> Use the cdktf.json file to customize configuration settings and define the providers and modules to use with your application.

The `cdktf.json` file is where you can supply custom configuration settings for your application and define the [providers](/concepts/providers) and [modules](/concepts/modules) that you want to use. When you initialize a new CDK Terrain project with a [built-in template](/create-and-deploy/project-setup), the template generates a basic `cdktf.json` file in your root directory that you can customize for your application. Refer to the [Project Setup documentation](/create-and-deploy/project-setup) for more information about initializing a new project.

## Specification

```typescript theme={null}
export enum Language {
  TYPESCRIPT = "typescript",
  PYTHON = "python",
  CSHARP = "csharp",
  JAVA = "java",
  GO = "go",
}

export interface TerraformDependencyConstraint {
  readonly name: string; // name of the module / provider
  readonly source?: string; // path / url / registry identifier for the module / provider
  readonly version?: string; // version constraint (https://www.terraform.io/language/providers/requirements.html#version-constraints)
}
type RequirementDefinition = string | TerraformDependencyConstraint;

export interface Config {
  readonly app?: string; // The command to run in order to synthesize the code to Terraform compatible JSON
  readonly language?: Language; // Target language for building provider or module bindings. Currently supported: `typescript`, `python`, `java`, `csharp`, and `go`
  readonly output: string; // Default: 'cdktf.out'. Where the synthesized JSON should go. Also will be the working directory for Terraform operations
  readonly codeMakerOutput: string; // Default: '.gen'. Path where generated provider bindings will be rendered to.
  readonly projectId: string; // Default: generated UUID. Unique identifier for the project used to differentiate projects
  readonly sendCrashReports: boolean; // Default: false. Whether to send crash reports to the CDKTN team
  readonly terraformProviders?: RequirementDefinition[]; // Terraform Providers to build
  readonly terraformModules?: RequirementDefinition[]; // Terraform Modules to build
  readonly targetVersions?: { terraform?: string; opentofu?: string }; // npm semver ranges per product the project supports. Default: { terraform: '>=1.5.7', opentofu: '>=1.6.0' }
  readonly validateInstalledBinary?: boolean; // Default: false. When true, `diff`, `deploy`, and `destroy` verify the installed Terraform/OpenTofu binary satisfies `targetVersions` before running
}
```

## Minimal Configuration

The most basic configuration only defines `app`. This is useful when you plan to use [pre-built providers](/concepts/providers#install-pre-built-providers) and you don't need to generate any provider or module bindings.

```json theme={null}
{
  "app": "npm run --silent compile && node main.js"
}
```

## Declare Providers and Modules

You must declare all of the providers and modules that require code bindings in your `cdktf.json` file. CDKTN generates these code bindings from `cdktf.json` when you run `cdktn get`. We have a selection of pre-built [providers](/concepts/providers#install-pre-built-providers) available, but you may occasionally want to re-generate the code bindings for those providers yourself. For example, you may need a different version of that provider than the pre-built package. We do not provide pre-built modules, so you must always declare them in your `cdktf.json` file.

The [schema](https://developer.hashicorp.com/terraform/language/providers/requirements#source-addresses) for both providers and modules in CDK Terrain consists of a name, a [source](https://developer.hashicorp.com/terraform/language/providers/requirements#source-addresses), and a [version constraint](https://developer.hashicorp.com/terraform/language/providers/requirements#version-constraints).

You can declare providers and modules using either JSON or a string with the format `source@ ~> version`.

### Provider Source

* **HashiCorp providers**: You can specify official HashiCorp [maintained providers](https://registry.terraform.io/browse/providers?tier=official) by their name on the Terraform Registry. For example, you can use `aws` to declare the official [AWS provider](https://registry.terraform.io/providers/hashicorp/aws/latest): `aws@ ~> 2.0`

* **Community providers**: You must provide the fully-qualified name. The fully-qualified name is available on the provider's registry page. For example, to define the [DataDog provider](https://registry.terraform.io/providers/DataDog/datadog/latest): `DataDog/datadog@ ~> 3.4.0`

### Module Source

* For modules on the Terraform Registry, provide the the full registry namespace. For example, to define the [AWS VPC module](https://registry.terraform.io/modules/terraform-aws-modules/vpc/aws/latest): `terraform-aws-modules/vpc/aws@ ~> 3.2.0`.

* For local modules, please use the object format to ensure that CDKTN can properly name the generated classes.

  ```jsonc theme={null}
  {
    // ...
    "terraformModules": [
      {
        "name": "myLocalModule",
        "source": "../my-modules/local-module",
      },
    ],
  }
  ```

### Version Constraint

When you declare providers and modules in the string format, add the [version constraint](https://developer.hashicorp.com/terraform/language/expressions/version-constraints#version-constraint-syntax) after the provider or module name separated by an `@`. For example, so `provider|module@ ~> version`. The version constraint is optional; when you omit the version constraint, CDK Terrain will download and use the latest version.

When you declare providers in JSON, add the constraint in the `version` property.

```jsonc theme={null}
{
  //...
  "terraformProviders": [
    {
      "name": "aws",
      "source": "hashicorp/aws",
      "version": "~> 3.22",
    },
  ],
}
```

## Declare Target Runtimes

The optional `targetVersions` field declares the Terraform and OpenTofu version ranges your project intends to support. CDK Terrain validates your configuration against this declaration at synthesis time — for example, the [function availability validation](/concepts/functions#function-availability-across-terraform-and-opentofu) checks that the Terraform functions you use are available across every version you target — without ever executing a binary.

Declare a range per product as an [npm semver range](https://github.com/npm/node-semver#ranges), keyed by `terraform` and/or `opentofu`:

```json theme={null}
{
  "app": "npm run --silent compile && node main.js",
  "targetVersions": {
    "terraform": ">=1.5.7",
    "opentofu": ">=1.6.0"
  }
}
```

Omitting a product means your project does not target it. When you omit `targetVersions` entirely, CDK Terrain assumes the most portable interpretation — every supported release of both products: `{ "terraform": ">=1.5.7", "opentofu": ">=1.6.0" }`.

<Warning>
  Values must be npm semver ranges (for example `>=1.5.7` or `~1.5.7`), not Terraform's `~>` pessimistic constraint syntax. CDK Terrain validates `targetVersions` when it parses `cdktf.json` and fails with an error if a range is malformed or uses `~>`.
</Warning>

### Validate the Installed Binary

The declarative checks above never run Terraform or OpenTofu, so they behave identically in CI, package builds, and environments without either installed. To additionally verify that the binary actually installed on a machine falls inside your declared `targetVersions`, opt in with `validateInstalledBinary`:

```json theme={null}
{
  "targetVersions": {
    "terraform": ">=1.5.7"
  },
  "validateInstalledBinary": true
}
```

When `validateInstalledBinary` is `true` (default `false`), the commands that execute the Terraform-compatible CLI — `diff`, `deploy`, and `destroy` — check the installed binary before running it. The command fails if:

* the binary cannot be identified as Terraform or OpenTofu,
* its product is not declared in `targetVersions`, or
* its version falls outside the declared range.

## Configure Files to Watch

When using `cdktn watch`, CDKTN inspects the `cdktf.json`s `watchPattern` property to determine which files to watch. If you do not specify a `watchPattern` property, CDKTN adds the default watch pattern for your language on the first run. The `watchPattern` expects an array of glob patterns, e.g. `["main.ts", "../constructs/**/*.ts", "lib/*.ts"]`.

## Configuration Examples

### Change the Output Directory

Defining `output` changes the directory where `cdktn` stores your generated Terraform configuration file. Terraform performs all operations within this directory.

The following example synthesizes the JSON Terraform configuration into `my-workdir`:

```json theme={null}
{
  "app": "npm run --silent compile && node main.js",
  "output": "my-workdir"
}
```

### Build Providers

With the following `terraformProviders` configuration, a `cdktn get` builds the latest AWS provider within the 2.X version range. CDKTN saves the generated code in in `.gen` by default. You can adjust this behavior with `codeMakerOutput`. Refer to the other examples on this page.

```json theme={null}
{
  "language": "typescript",
  "app": "npm run --silent compile && node main.js",
  "terraformProviders": ["aws@~> 2.0"]
}
```

### Build Modules

With the following `terraformModules` configuration, a `cdktn get` builds the latest `terraform-aws-modules/vpc/aws` module from the Terraform Registry. The generated code will be saved into `.gen` by default. You can adjust this behavior with `codeMakerOutput`. Refer to the other examples on this page.

```json theme={null}
{
  "language": "typescript",
  "app": "npm run --silent compile && node main.js",
  "terraformModules": ["terraform-aws-modules/vpc/aws"]
}
```

### Build Providers & Modules

With the following example configuration, a `cdktn get` builds both the AWS provider and the latest `terraform-aws-modules/vpc/aws` module from the Terraform Registry.

```json theme={null}
{
  "language": "typescript",
  "app": "npm run --silent compile && node main.js",
  "terraformModules": ["terraform-aws-modules/vpc/aws"],
  "terraformProviders": ["aws@~> 2.0"]
}
```

### Build Multiple Providers

You can also build multiple providers or modules. The following example builds multiple providers.

```json theme={null}
{
  "language": "typescript",
  "app": "npm run --silent compile && node main.js",
  "terraformProviders": [
    "null",
    "aws",
    "google",
    "azurerm",
    "kubernetes",
    "consul",
    "vault",
    "nomad"
  ]
}
```

### Build Providers in Custom Directory

The following configuration generates the `aws` provider bindings in the folder `./imports`. The Python template uses this method to make it easier to reference the generated classes.

```json theme={null}
{
  "language": "python",
  "app": "pipenv run ./main.py",
  "terraformProviders": ["aws@~> 2.0"],
  "codeMakerOutput": "imports"
}
```

### Enable Crash Reporting for the CLI

You can enable or disable crash reporting by setting the `sendCrashReports` property to `true` or `false`. Sending crash reports helps our team improve the CLI faster. Refer to [Telemetry](/telemetry#crash-reporting) for more information about what we track.

```json theme={null}
{
  "language": "typescript",
  "app": "npm run --silent compile && node main.js",
  "sendCrashReports": true
}
```
