0

I'm deploying a google_compute_instance with Terraform. That instance should run a script when its created. Using the property metadata_startup_script:

resource "google_compute_instance" "couchbase_host" {
   ...

   metadata_startup_script = file("vm_setup.sh")
}

Where vm_setup.sh:

program --arg ${var.my_value}

file() extracts to a raw string, meaning the variable is not populated. How can I use a terraform variable in my .sh? I'm trying to avoid heredoc << EOF .. because my script is somewhat long.

OrangePot
  • 1,053
  • 2
  • 14
  • 38
  • 1
    Yes, its possible. I have Deleted an answer i had posted. There is an existing Post that has the answer for TF 12 and earlier version.. Please check: https://stackoverflow.com/questions/50835636/accessing-terraform-variables-within-user-data-provider-template-file – Giridhar Oct 06 '20 at 00:48

1 Answers1

1

The templatefile function is similar to the file function in that it reads a given file from disk, but it also additionally interprets the contents of the file as a string template, so you can insert external values into it.

For example:

   metadata_startup_script = templatefile("${path.module}/vm_setup.sh.tmpl", {
     arg_value = var.my_value
   })

In the template file you can use ${arg_value} to substitute the given value from the object in the second argument to templatefile.


Please note that with just a direct reference to the value the result will not necessarily be valid shell syntax -- the caller could potentially set var.my_value to something that would be misinterpreted by the shell. One way to avoid that would be to use the replace function to apply single-quoting to the value, assuming this script will ultimately be evaluated by a Unix-style shell (bash, etc):

program --arg '${replace(arg_value, "'", "'\\''")}'

If arg_value had the value I'm a troublemaker then the above template would produce the following result:

program --arg 'I'\''m a troublemaker'

...where the surrounding ' quote characters and the special escaping of the ' in the string should cause the shell to interpret the value literally, exactly as provided by the caller of your module.

Martin Atkins
  • 62,420
  • 8
  • 120
  • 138