How are debug: var=vars / var=hostvars supposed to work?

1,084 views
Skip to first unread message

Ross Rosen

unread,
Oct 15, 2014, 4:31:50 PM10/15/14
to ansible...@googlegroups.com
Per the documentation and this thread: https://groups.google.com/d/msg/ansible-project/rE8aVu4LNS0/sGKweGPvffoJ
I *think* that debug: var=hostvars should print all the variables in scope (for each host).  I'm not sure what var=vars is - non-host-specific variables?

In either case, I'm getting extremely odd behavior that I can't figure out.  I'm sorry this is long, but it is hopefully easy to follow and I suspect is either a simple answer or there is a bug.

(some stuff removed for brevity or security)

Here is my command line: 
     ansible-playbook playbook.yml --inventory-file dynamic_inventory.sh --limit stage --user xxx --private-key xxx.pub -e IS_VAGRANT=False -C
    
Here is the result of my dynamic inventory for host 'stage'
    {
        "hosts": [
            "192.xxx.xxx.176"
        ],
        "vars": {
            "HOST_NAME": "stage.yyyyyyyyy.com",
            "SERVER_NAME": "stage.yyyyyyyyy.com"
        }
    }

Now here are the key plays, and results, from my playbook

- debug: var=vars
>> This looks pretty good (but note it doesn't show variables from my inventory)

    PLAY [all] ********************************************************************

    TASK: [baseUbuntu | debug var=vars] *******************************************
    ok: [192.xxx.xxx.176] => {
        "vars": {
            "DIFFTOOL": "git --no-pager diff",
            ... <DELETED - but *no* HOST_NAME> ...
            "IS_VAGRANT": "False",
            ... <DELETED - but *no* SERVER_NAME> ...
            "_original_file": "/Users/xxxxxx/tmp/thissite/ansible_config/roles/baseUbuntu/tasks/main.yml",
            "always_run": false,
            "changed_when": null,
            "delegate_to": null,
            ... <DELETED> ...
            "role_uuid": "160302ff-f06f-4a78-8204-f0fcc4a8c750"
        }
    }



- debug: var=hostvars
>> This looks wrong to me. Shouldn't it either be a superset of vars and my inventory variables? 
(HOST_NAME and SERVER_NAME)

    TASK: [baseUbuntu | debug var=hostvars] ***************************************
    ok: [192.xxx.xxx.176] => {
        "hostvars": {
            "192.xxx.xxx.176": {
                "IS_VAGRANT": "False"
            }
        }
    }



Hmmm... maybe I I'm not properly setting my inventory variables.
Nope! See 'HOST_NAME' is properly set. Why doesn't it show up in vars or hostvars?

- debug: msg="HOST_NAME = *{{ HOST_NAME }}*"
    TASK: [baseUbuntu | debug msg="HOST_NAME = *{{ HOST_NAME }}*"] ****************
    ok: [192.xxx.xxx.176] => {
        "msg": "HOST_NAME = *stage.yyyyyyyyy.com*"
    }


And this one is even weirder. I use {{ HOST_NAME }} and in the "name" clause it doesn't 
render and in the hostname clause it does!

- name: "Set hostname to {{ HOST_NAME }}"
    hostname: name="{{ HOST_NAME }}"

    TASK: [baseUbuntu | debug msg="HOST_NAME = *{{ HOST_NAME }}*"] ****************
    ok: [192.xxx.xxx.176] => {
        "msg": "HOST_NAME = *stage.yyyyyyyyy.com*"
    }


I'm baffled - I'd appreciate any tips. Thank you!

Michael DeHaan

unread,
Oct 20, 2014, 5:14:04 PM10/20/14
to ansible...@googlegroups.com
"I *think* that debug: var=hostvars should print all the variables in scope (for each host)"

It doesn't do this, but rather looks for variable names inside hostvars.

You can think of the "hostvars" syntax as a way to reference variables for other hosts.

I guess whether it should work might be a technicality, but that's what it was intended for.


--
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/474c431e-8108-4739-a31d-f1c0461d76c2%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Michael Hoglan

unread,
Oct 22, 2014, 7:55:07 PM10/22/14
to ansible...@googlegroups.com
Ive stopped doing 
debug: var=hostvars 
and do 
debug: var=hostvars[inventory_hostname] 
or
debug: var=hostvars[item]
with_items: play_hosts 

As you do not get all the vars outputted in when you do it the first way, but the second way I do.  I am completely guessing as I have not dug into the code to see, but I am suspecting that hostvars is coming from a cache that is not up to date, and when you access the specific element in hostvars that is coming from a cache that contains the latest.

Thanks!
Michael

Serge van Ginderachter

unread,
Oct 23, 2014, 3:22:26 AM10/23/14
to ansible...@googlegroups.com
On 20 October 2014 23:12, Michael DeHaan <mic...@ansible.com> wrote:
"I *think* that debug: var=hostvars should print all the variables in scope (for each host)"

It doesn't do this, but rather looks for variable names inside hostvars.

You can think of the "hostvars" syntax as a way to reference variables for other hosts.

I guess whether it should work might be a technicality, but that's what it was intended for.


​Yes, 'hostvars' is implemented  as a caching dictionary, which means you need to explicitly request vars for a particular key/host.​

Michael Hoglan

unread,
Oct 23, 2014, 9:50:37 AM10/23/14
to ansible...@googlegroups.com
I know there probably internal implementation details on why it is the way it is, but wouldn't we want debug: var=hostvars to not come from the cache and be the latest truth of what is contained in hostvars?  If I am doing a debug of the variable, I am already in a mode where performance is not a concern, I am trying to gather insight into the state of the system.  So maybe if the debug task is used, the variable in the task should be fully interpolated, or unioned with the rest of dictionaries / lists that are accessed when specifying hostvars[hostname]
  

Thanks!
Michael

Michael DeHaan

unread,
Oct 24, 2014, 9:21:43 AM10/24/14
to ansible...@googlegroups.com
"but wouldn't we want debug: var=hostvars to not come from the cache and be the latest truth of what is contained in hostvars"

Serge mispoke a bit above.  The problem is not that hostvars is a cache, but rather that hostvars is an object that provides access to individual variables.

We aren't really concerned with:

- debug: var=hostvars

as it's a very unusual thing to do.

typically this is how vars are shown with debug:

- hosts: webservers
  tasks:
     - debug: var=foo

And the "hostvars" trick is only needed when accessing variables from *other* servers, typically in templates for instance when building out something like an iptables config.





--
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.
Reply all
Reply to author
Forward
0 new messages