Compatibility
Pulumi’s guide offers routes that keep your HCL as well as routes that convert it:
- Pulumi Cloud as the state backend. Pulumi Cloud implements the Terraform remote backend API, so you add a standard
backend "remote"block and keep running the Terraform or OpenTofu CLI. - Pulumi HCL. A
Pulumi.yamlwithruntime: hclruns your existing.tffiles on the Pulumi engine. - Terraform modules in a Pulumi program.
pulumi package add hcl module <source> [<version>]generates a local SDK for a registry or local module. - Referencing Terraform state.
terraform.state.getLocalReferenceandgetRemoteReferenceread outputs from a.tfstatefile or a remote backend, so new Pulumi stacks can build on resources Terraform still manages.
Before you switch
To convert the code yourself:
- Run
pulumi convert --from terraform --language <typescript|python|go|csharp>in the folder holding the HCL. Variables, outputs, resources, data sources and modules (as Pulumi components) are supported, along with almost all HCL2 expressions. - Import the existing resources with
pulumi import --from terraform ./terraform.tfstate. Imported resources are marked protected. If you stay onruntime: hcl, usepulumi import --from hcl terraform.tfstatefrom the project directory instead. - Run
pulumi previewand expect no changes before the firstpulumi up.
The guide also describes a state-first route with the pulumi-terraform-migrate plugin (pulumi plugin run terraform-migrate -- stack --from ... --to ... --out ... --plugins ...), which writes a Pulumi state file and a list of required plugins, followed by pulumi stack import. It has to be repeated for each Terraform stack. Pulumi’s recommended route is Neo, its hosted agent, which needs Pulumi Neo access, the Pulumi GitHub app and cloud credentials in Pulumi ESC.
Pitfalls
- Pulumi does not reuse a Terraform state file in place. State lives in whichever backend
pulumi loginpoints at, so resources have to be imported even when the code stays in HCL. pulumi convertsucceeds even on features it cannot handle, and leavesnotImplementedcalls to fill in by hand. Pulumi puts the share of code converted without such TODOs at 90 to 95% for most projects.pulumi import --from hclskips resources nested inside modules, with a warning. Import those separately.- Paths relative to the Terraform project usually need rewriting relative to the generated program file.
pulumi-terraform-migrateneeds the OpenTofu CLI (tofu) on yourPATH, and its intermediate state needs onepulumi upto complete.- Neo may not handle modules with complex dynamic blocks, custom providers or unusual state. Those need the manual routes.