The default behavior of Terraform is that, when executing the terraform init command, the version of the Terraform binary (which we will call the Command-Line Interface (CLI), as explained here: https://www.terraform.io/docs/glossary.html#cli) used is the one installed on the local workstation. In addition, this command downloads the latest version of the providers used in the code.
However, for compatibility reasons, it is always advisable to avoid surprises so that you can specify which version of the Terraform binary is going to be used in the Terraform configuration. The following are some examples:
- A Terraform configuration written with HCL 2 must indicate that it has to be executed with a Terraform version greater than or equal to 0.12.
- A Terraform configuration that contains new features such as count and for_each in modules must indicate that it has to be executed with a Terraform version greater than or equal to 0.13.
In the same vein and for the same reasons of compatibility, we may want to specify the provider version to be used.
In this recipe, we will learn how to specify the Terraform version, as well as the provider version.
Getting ready
To start this recipe, we will write a basic Terraform configuration file that contains the following code:
variable "resource_group_name" {
default = "rg_test"
}
resource "azurerm_resource_group" "rg" {
name = var.resource_group_name
location = "West Europe"
}
resource "azurerm_public_ip" "pip" {
name = "bookip"
location = "West Europe"
resource_group_name = azurerm_resource_group.rg.name
public_ip_address_allocation = "Dynamic"
domain_name_label = "bookdevops"
}
This example code provides resources in Azure (a Resource Group and a public IP address). For more details, read the following documentation about the Terraform AzureRM provider: https://www.terraform.io/docs/providers/azurerm/index.html
Finally, when executing the terraform plan command inside this code, we get the following warning message:
This means that, currently, this Terraform configuration is still compatible with the latest version of the provider but that in a future version of the provider, this property will be changed and therefore this code will no longer work.
Now, let's discuss the steps we need to follow to make the following compliances:
- This configuration can only be executed if Terraform 0.13 (at least) is installed on the local computer.
- Our current configuration can be executed even if the azurerm provider evolves with breaking changes.
We'll take a look at this next.
How to do it…
To specify the Terraform version to be installed on the local workstation, do the following:
- In the Terraform configuration, add the following block:
terraform {
required_version = ">= 0.13"
}
- To specify the provider source and version to use, we need to add the required_provider block inside the same terraform configuration block:
terraform {
...
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "2.10.0"
}
}
}
How it works…
When executing the terraform init command, Terraform will check that the version of the installed Terraform binary that executes the Terraform configuration file corresponds to the version specified in the required_version property of the terraform block.
If it matches, it won't throw an error as it is greater than version 0.13. Otherwise, it will throw an error:
With regard to the specification of the provider version, when executing the terraform init command, if no version is specified, Terraform downloads the latest version of the provider, otherwise it downloads the specified version, as shown in the following two screenshots.
The following screenshot shows the provider plugin being downloaded from the specified source without us specifying the required version (at the time of writing, the latest version of the provider is 2.20.0):
As we can see, the latest version of the azurerm provider (2.20.0) has been downloaded.
In addition, the following screenshot shows the azurerm provider plugin being downloaded when we specify the required version (2.10.0):
As we can see, the specified version of the azurerm provider (2.10.0) has been downloaded.
In this required_version block, we also add the source property, which was introduced in version 0.13 of Terraform and is documented here: https://github.com/hashicorp/terraform/blob/master/website/upgrade-guides/0-13.html.markdown#explicit-provider-source-locations
There's more…
In this recipe, we learned how to download the azurerm provider in various ways. What we did here applies to all providers you may wish to download.
It is also important to mention that the version of the Terraform binary that's used is specified in the Terraform state file. This is to ensure that nobody applies this Terraform configuration with a lower version of the Terraform binary, thus ensuring that the format of the Terraform state file conforms with the correct version of the Terraform binary.
See also
- For more information about the properties of the Terraform block, go to https://www.terraform.io/docs/configuration/terraform.html.
- For more information about the properties of the providers, go to https://www.terraform.io/docs/configuration/providers.html.
- More information about Terraform binary versioning is documented at https://www.terraform.io/docs/extend/best-practices/versioning.html.
- The upgrade guide for the azurerm provider (to version 2.0) is available at https://www.terraform.io/docs/providers/azurerm/guides/2.0-upgrade-guide.html.