Help passing list from Ansible to Terraform list variable

58 views
Skip to first unread message

Stephen Nesbitt

unread,
Dec 23, 2018, 3:07:12 PM12/23/18
to Ansible Project
All:

I am using the terraform module and have a terraform plan that contains a list type variable. (Ansible 2.7.2)

It may be my lack of deep knowledge of YAML, but every attempt I've tried, results in a validation error.

My suspicion is that terraform expects the list to be passed in a certain format. This is based on the terraform docs which show that one can pass a list in as environment variable with the format:
$ TF_VAR_somelist='["ami-abc123", "ami-bcd234"]' terraform plan

But I have been utterly unable to figure out how to pass this format from Ansible (i.e. yaml) to Terraform.

Does anyone know how I can get this to work without resorting to an environment variable.

Thx,

-steve

Karl Auer

unread,
Dec 23, 2018, 5:42:45 PM12/23/18
to ansible-project
I haven't used the terraform module. but have just had a look at the Ansible doc for it, and it describes a "variables" parameter as "a group of key-values to override template variables or those in variables files." Seems that this format in ansible would work to pass that parameter:

- terraform:
      [...]
      variables:
          plain_var: "string value"
          list_var: [ "list_element1", "list_element_2" ]
          map_var:
              one_thing: "blah"
              otherthing: "bloo"
      [...]

Note that "variables" is the literal name of the attribute; it is literally the word "variables".

However, I suspect that "plain_var", "list_var" etc need to be variable names that Terraform expects to see, and the contents have to be forms that Terraform expects.
I can see several ways this might not be working:
  • you have a syntax error in your Ansible code; this would cause an error message from Ansible, and Terraform would not be called at all.
  • you are not using the "variables" attribute, and are trying to pass the variable directly as an attribute to the terraform module. This would cause some kind of "unrecognised attribute" error in Ansible, and Terraform would not be called at all.
  • you are using the "variables" attribute, but passing a variable name in it that Terraform doesn't know about; this would cause some kind of error in Terraform
  • you are using the "variables" attribute and you are using a variable name known to Terraform, but the contents of the variable you are passing are in some way incomplete or defective. This would cause some kind of error in Terraform.
It would be helpful to see the actual code you are trying and the actual errors produced when you do.

Regards, K.

--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
To post to this group, send email to ansible...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/ansible-project/3944fde6-c611-41ff-8f95-aa21ecf461c0%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


--
Karl Auer

Email  : ka...@2pisoftware.com
Website: http://2pisoftware.com


GPG/PGP : 958A 2647 6C44 D376 3D63 86A5 FFB2 20BC 0257 5816
Previous: F0AB 6C70 A49D 1927 6E05 81E7 AD95 268F 2AB6 40EA

Stephen Nesbitt

unread,
Dec 24, 2018, 1:27:41 PM12/24/18
to Ansible Project
Hi Karl:

Thanks for the reply. I was hoping it was something obvious :-). This is with Ansible 2.7.4 and Terraforn 0.11.11. Currently my workaround is to pass it in through an environment variable which would not be my preferred means.

Following are the details:

Ansible playbook:  TF_LOG=DEBUG ansible-playbook -i localhost -vvvv test_terraform_list.yaml
---
- hosts: localhost
  become
: false

  tasks
:
   
- name: Test Terraform List
      terraform
:
        project_path
: "/home/snesbitt/Projects/devops/ansible/terraform/sandbox"
        state
: present
        variables
:
          test_list
: [ "list_element1", "list_element_2" ]
          test2
: "Hi"



The Terraform plan:
variable "test_list" {
  type
= "list"
}

variable
"test2" {}

provider
"zerotier" {
  api_key
= "XXXX"

}

And the output:

ansible-playbook 2.7.4
  config file
= None
  configured
module search path = ['/home/snesbitt/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules']
  ansible python
module location = /home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/lib/python3.6/site-packages/ansible
  executable location
= /home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/bin/ansible-playbook
  python version
= 3.6.7 (default, Oct 22 2018, 11:32:17) [GCC 8.2.0]
No config file found; using defaults
setting up inventory plugins
/home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost did not meet host_list requirements, check plugin documentation if this is unexpected
Skipping due to inventory source not existing or not being readable by the current user
/home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost did not meet script requirements, check plugin documentation if this is unexpected
Skipping due to inventory source not existing or not being readable by the current user
/home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost did not meet yaml requirements, check plugin documentation if this is unexpected
Skipping due to inventory source not existing or not being readable by the current user
/home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost did not meet ini requirements, check plugin documentation if this is unexpected
/home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost did not meet auto requirements, check plugin documentation if this is unexpected
 
[WARNING]: Unable to parse /home/snesbitt/Projects/devops/ansible/terraform/sandbox/localhost as an inventory source

 
[WARNING]: No inventory was parsed, only implicit localhost is available

 
[WARNING]: provided hosts list is empty, only localhost is available. Note that the implicit localhost does not match 'all'

Loading callback plugin default of type stdout, v2.0 from /home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/lib/python3.6/site-packages/ansible/plugins/callback/default.py

PLAYBOOK
: test_terraform_list.yaml ***************************************************************************************************************************************************************
1 plays in test_terraform_list.yaml

PLAY
[localhost] *********************************************************************************************************************************************************************************

TASK
[Gathering Facts] ***************************************************************************************************************************************************************************
task path
: /home/snesbitt/Projects/devops/ansible/terraform/sandbox/test_terraform_list.yaml:2
<127.0.0.1> ESTABLISH LOCAL CONNECTION FOR USER: snesbitt
<127.0.0.1> EXEC /bin/sh -c 'echo ~snesbitt && sleep 0'
<127.0.0.1> EXEC /bin/sh -c '( umask 77 && mkdir -p "` echo /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111 `" && echo ansible-tmp-1545670798.8773258-51417051836111="` echo /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111 `" ) && sleep 0'
Using module file /home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/lib/python3.6/site-packages/ansible/modules/system/setup.py
<127.0.0.1> PUT /home/snesbitt/.ansible/tmp/ansible-local-93401_0r0s9e/tmpqi9zh2or TO /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111/AnsiballZ_setup.py
<127.0.0.1> EXEC /bin/sh -c 'chmod u+x /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111/ /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111/AnsiballZ_setup.py && sleep 0'
<127.0.0.1> EXEC /bin/sh -c '/home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/bin/python3.6 /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111/AnsiballZ_setup.py && sleep 0'
<127.0.0.1> EXEC /bin/sh -c 'rm -f -r /home/snesbitt/.ansible/tmp/ansible-tmp-1545670798.8773258-51417051836111/ > /dev/null 2>&1 && sleep 0'
ok
: [localhost]
META
: ran handlers

TASK
[Test Terraform List] ***********************************************************************************************************************************************************************
task path
: /home/snesbitt/Projects/devops/ansible/terraform/sandbox/test_terraform_list.yaml:6
<127.0.0.1> ESTABLISH LOCAL CONNECTION FOR USER: snesbitt
<127.0.0.1> EXEC /bin/sh -c 'echo ~snesbitt && sleep 0'
<127.0.0.1> EXEC /bin/sh -c '( umask 77 && mkdir -p "` echo /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643 `" && echo ansible-tmp-1545670799.7136817-89538225081643="` echo /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643 `" ) && sleep 0'
Using module file /home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/lib/python3.6/site-packages/ansible/modules/cloud/misc/terraform.py
<127.0.0.1> PUT /home/snesbitt/.ansible/tmp/ansible-local-93401_0r0s9e/tmpapns9wkv TO /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643/AnsiballZ_terraform.py
<127.0.0.1> EXEC /bin/sh -c 'chmod u+x /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643/ /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643/AnsiballZ_terraform.py && sleep 0'
<127.0.0.1> EXEC /bin/sh -c '/home/snesbitt/.local/share/virtualenvs/ansible-8A5NQYXv/bin/python3.6 /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643/AnsiballZ_terraform.py && sleep 0'
<127.0.0.1> EXEC /bin/sh -c 'rm -f -r /home/snesbitt/.ansible/tmp/ansible-tmp-1545670799.7136817-89538225081643/ > /dev/null 2>&1 && sleep 0'
fatal
: [localhost]: FAILED! => {
   
"changed": false,
   
"invocation": {
       
"module_args": {
           
"backend_config": null,
           
"binary_path": null,
           
"force_init": false,
           
"lock": true,
           
"lock_timeout": null,
           
"plan_file": null,
           
"project_path": "/home/snesbitt/Projects/devops/ansible/terraform/sandbox",
           
"purge_workspace": false,
           
"state": "present",
           
"state_file": null,
           
"targets": [],
           
"variables": {
               
"test2": "Hi",
               
"test_list": [
                   
"list_element1",
                   
"list_element_2"
               
]
           
},
           
"variables_file": null,
           
"workspace": "default"
       
}
   
},
   
"msg": "Failed to validate Terraform configuration files:\r\n2018/12/24 08:59:59 [INFO] Terraform version: 0.11.11  ac4fff416318bf0915a0ab80e062a99ef3724334\n2018/12/24 08:59:59 [INFO] Go runtime version: go1.11.1\n2018/12/24 08:59:59 [INFO] CLI args: []string{\"/usr/local/bin/terraform_0.11.11/terraform\", \"validate\", \"-var\", \"'test_list=['\\\"'\\\"'list_element1'\\\"'\\\"', '\\\"'\\\"'list_element_2'\\\"'\\\"']'\", \"-var\", \"test2=Hi\"}\n2018/12/24 08:59:59 [DEBUG] Attempting to open CLI config file: /home/snesbitt/.terraformrc\n2018/12/24 08:59:59 [DEBUG] File doesn't exist, but doesn't need to. Ignoring.\n2018/12/24 08:59:59 [INFO] CLI command args: []string{\"validate\", \"-var\", \"'test_list=['\\\"'\\\"'list_element1'\\\"'\\\"', '\\\"'\\\"'list_element_2'\\\"'\\\"']'\", \"-var\", \"test2=Hi\"}\n\u001b[31mUsage: terraform validate [options] [dir]\n\n  Validate the terraform files in a directory. Validation includes a\n  basic check of syntax as well as checking that all variables declared\n  in the configuration are specified in one of the possible ways:\n\n      -var foo=...\n      -var-file=foo.vars\n      TF_VAR_foo environment variable\n      terraform.tfvars\n      default value\n\n  If dir is not specified, then the current directory will be used.\n\nOptions:\n\n  -check-variables=true If set to true (default), the command will check\n                        whether all required variables have been specified.\n\n  -no-color             If specified, output won't contain any color.\n\n  -var 'foo=bar'        Set a variable in the Terraform configuration. This\n                        flag can be set multiple times.\n\n  -var-file=foo         Set variables in the Terraform configuration from\n                        a file. If \"terraform.tfvars\" is present, it will be\n                        automatically loaded if this flag is not specified.\u001b[0m\u001b[0m\n2018/12/24 08:59:59 [DEBUG] plugin: waiting for all plugin processes to complete...\n"
}
        to
retry, use: --limit @/home/snesbitt/Projects/devops/ansible/terraform/sandbox/test_terraform_list.retry

PLAY RECAP
***************************************************************************************************************************************************************************************
localhost                  
: ok=1    changed=0    unreachable=0    failed=1  

Karl Auer

unread,
Dec 24, 2018, 8:43:06 PM12/24/18
to ansible-project
Wild shot in the dark, try this:

      variables:
          - test_list
: [ "list_element1", "list_element_2" ]
          - test2
: "Hi"

That's a list of maps...

Regards, K.

   - test


For more options, visit https://groups.google.com/d/optout.
Reply all
Reply to author
Forward
0 new messages