Quoting types and identifiers

Working on a configuration recently, I created a resource but forgot to quote the type and name. Eg instead of:

resource "null_resource" "my_resource" { ... }

I typed:

resource null_resource my_resource { ... }

Surprisingly (to me), it worked. No errors or warnings were generated, and the configuration functioned as intended. I carried the experiment further, and eliminated all quoting that wasn’t surrounding string data.

variable my_var {}
provider null { }
resource null_resource my_resource {
  provisioner local-exec { command = "echo my_var is ${my_var}" }
}

I started quote elimination with beta 0.13, but it appears to apply equally well with 0.12.25. The text is significantly easier to read without them. Errors due to unmatched quotes are reduced.
To illustrate, consider this obvious mistake:

resource "TYPE" "NAME {
  something = var.something_else
  another = var.one
  lastvar = "this"
}

Without syntax coloring, it’s easy to overlook:

resource "TYPE" "NAME {
  something = var.something_else
  another = var.one
  lastvar = "this"
}

Is quoting types, variable declaractions, etc theoretically required by the language syntax?

1 Like

Hi @jeremykatz,

The Terraform documentation has shown the block labels quoted in all examples for many years, so that is the primary, idomatic style. terraform fmt may start doing this automatically in future versions, as it starts to regain some of its more opinionated formatting behaviors that were temporarily removed in Terraform 0.12 because of the switch to a new HCL implementation.

As you’ve seen though, the parser considers them optional mainly for backward compatibility with earlier versions of the language, which have considered quoted and unquoted labels as synonymous going back to the introduction of HCL in a very early Terraform version.

If anyone is taking a poll, my vote is for fewer "s.

1 Like

Please no. Why enforce adding unnecessary double quotes. They are ugly and make reading the code more difficult.
Yes, the doco has them, but the effort should instead be to clean up the doco, rather than try to force everyone to make their code harder to read.
What an awful choice.
A huge thumbs down to this.

and on the topic of consistency, why is it a good idea to try to enforce using double quotes when a resource is defined, but then later when that resource is referred to, it is without double quotes i.e. TYPE.NAME. If you really want consistency and doubles quotes are your thing, then enforce double quotes around the references as well i.e. “TYPE”.“NAME”.
Then terraform can be the language of most double quotes.

Hi all,

For what it’s worth I agree with you that if this had been my decision to make back at the start of Terraform’s life then I wouldn’t have placed these identifiers in quotes, but it’s not worth discussing now because this is the long-established idiomatic style and it isn’t going to change. Being consistent with how Terraform code is written elsewhere is more important than writing code that matches our individual preferences.

The standard Terraform style has been standard for many years now and it’s too late to change it. You are welcome to your preferences and you can choose to write Terraform a different way if you and your team agree to – Terraform will accept it both ways, after all – but there is no path to changing the prevailing style this late in Terraform’s life.

As long as the parser is never updated to disallow block labels without quotes then at least we can choose.
In our case it became a problem recently, because we had been running on 0.13.5 and the fmt command did not return an error when block labels did not have quotes. But I was starting some new work and tried 1.3.9 and now fmt returns and error. Meaning I can’t use fmt as is in our pipelines. So my current workaround is to patch fmt.go, which is just taking out one line. But there’s quite a bit of work to do that. Now I can’t use the hashicorp docker images unedited, and have to create my own.
Is there any chance that we at least get some switches for fmt.go, that would allow unquoted block labels ?

Maybe you want to instead be using terraform validate which is designed to check that the syntax of your code is correct, as opposed to fmt which is designed to reformat/check your code is adhering to the style guidelines (which you don’t want to be using).

Indeed, the behavior of allowing it both ways is covered by the Terraform 1.x Compatibility Promises, and so you can be sure that Terraform will not suddenly start rejecting it in future.

terraform fmt is documented as using one opinionated style that matches how Terraform is broadly used across many organizations and in Terraform’s own documentation. If you wish to adopt a “house style” that doesn’t match those rules then you should not run terraform fmt as part of your workflow.