Today we're going to compare the two best in class Infrastructure as Code tools — Pulumi and Terraform.
What is Terraform?
The industry standard infrastructure as code tool.
The primary way of creating Terraform configuration is in HashiCorp Configuration Language — a non-Turing complete, simple-to-write config language, heavily influenced by universal configuration language. It was designed explicitly for IaC.
Sometimes you'll hear "you have to go learn a custom language" to write Terraform. Hardly. HCL is intuitive and very very easy for anyone who programs.
Terraform is the industry standard
Frankly, Pulumi is a terraform alternative, not the other way around. The community, the support, the maturity — all of these are better with Terraform.
Terraform's CDK is coming
Terraform's Cloud Development Kit allows you to write TypeScript or Python that will generate Terraform configuration.
This can be seen as a direct Pulumi competitor. Part of me thinks that Pulumi's main purpose in the market is just to force Terraform to beef up its "real language" support. Whether Pulumi remains in the market or not, it will have that effect.
How is the CDK different from Pulumi?
Pulumi is farther along, and is more invested in this particular sub-arena (IaC in familiar programming languages)
What is Pulumi?
Pulumi is like Terraform, except you use familiar programming languages and tools. I've used it a good deal in TypeScript.
It uses Terraform under the hood.
Pulumi's Dynamic Providers are Amazing
Pulumi has a capability called dynamic providers. From the user's point of view, they are just an abstract class that you implement. You define CRUD operations, basically wrapping some API and exposing as much functionality as you want.
This is useful when something you want to use doesn't have a great Terraform provider, but has a great REST API. Dynamic providers make it easy for you to quickly provide a lot of value, within the framework of an IaC tool.
This is one of the biggest reasons I'm optimistic about Pulumi, especially when you compare it to Terraform's CDK.
Generating Pulumi Providers from Terraform ones is Tedious
The main reason creating a Pulumi provider from a Terraform provider is difficult is that it's not a standardized process.
In order to create a Pulumi provider from a working Terraform provider, you need to
- Fork pulumi-tf-provider-boilerplate. Follow the README
- Configure the
provider/resources.go. This is the meat of the task — the actual mapping of Terraform functions to Pulumi functions.
Now you have the SDK and the Pulumi plugin. Now for the tricky part.
Let's imagine we're only interested in Node.js, as I was when I did this. You have two pieces
- The NPM library
- the Pulumi plugin (
pulumi plugin ls)
I'm going to relax on the detail here, because I know I'm losing readers at this point. In short, you need to build a tar archive with the plugin, and deploy it in such a way that it's installed with the following command, right after the NPM library is installed (i.e. in the NPM post install script).
pulumi plugin install resource foo <version> --file=pulumi-resource-foo.tar.gz
All of that ^^^^^, is not trivial. I'm leaving out a lot of little details (feel free to contact me about them). It took me a long time to reverse engineer, with the help of the Pulumi community slack.
I believe this process is something they have down pat internally, but in the open source world haven't made first class yet.
If you're going to be doing a lot of this, it's going to weigh on your team. You should take that into consideration when you choose between the two.
So which is better?
I will say, they are both amazing tools. It depends what you're optimizing for.
- Terraform is more mature and lower risk, Pulumi is more cutting edge and potentially higher reward
- Pulumi is currently winning the "IaC in familiar languages" sub-arena, and really shines with dynamic providers
Ultimately the decisions depends on where you and your team are, and what you value.