# "Understanding Variable Precedence"

**URL:** <https://forum.ansible.com/t/understanding-variable-precedence/11827>\
**Category:** Ansible Project\
**Created:** [August 24, 2012, 11:29pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827 "2012-08-24T23:29:44Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![Michael\_DeHaan](https://avatars.discourse-cdn.com/v4/letter/m/c4cdca/32.png) [@Michael\_DeHaan](https://forum.ansible.com/u/Michael_DeHaan)\
**Post date:** [August 24, 2012, 11:29pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/1 "2012-08-24T23:29:44Z")

</div>

The question about how variables override each other has come up a few  
times in the last few days.

As a result, I added documentation on this to the "Advanced Playbooks"  
chapter, and am including that here so folks can see it.

There are no changes in current behavior, this is just documenting how  
things work. It's kind of amusing because I myself didn't know the  
order until I looked it up -- I mostly didn't do a lot of attempts to  
override variables and mostly rely on group and host variables when I  
need one to override the other -- though in the end, it works pretty  
well logically.

If you define a variable in a playbook, you have total assurance that  
value will be used.

If you want to play with overrides and such, group and host variables  
are the places you do that, with the variables for the 'all' group  
essentially being a global bucket that is optimal for defaults.

== START ==

You have already learned about inventory host and group variables,  
‘vars’, and ‘vars\_files’.

If a variable name is defined in more than one place with the same  
name, priority is as follows to determine which place sets the value  
of the variable.

&nbsp;&nbsp;&nbsp;&nbsp;Variables loaded from YAML files mentioned in ‘vars\_files’ in a playbook.  
&nbsp;&nbsp;&nbsp;&nbsp;‘vars’ as defined in the playbook.  
&nbsp;&nbsp;&nbsp;&nbsp;facts, whether built in or custom, or variables assigned from the  
‘register’ keyword.  
&nbsp;&nbsp;&nbsp;&nbsp;variables passed to parameterized task include statements.  
&nbsp;&nbsp;&nbsp;&nbsp;Host variables from inventory.  
&nbsp;&nbsp;&nbsp;&nbsp;Group variables from inventory, in order of least specific group  
to most specific.

Therefore, if you want to set a default value for something you wish  
to override somewhere else, the best place to set such a default is in  
a group variable.

== END ==

--Michael

---

<div class="post-metadata">

**Author:** ![Dave\_Peticolas](https://avatars.discourse-cdn.com/v4/letter/d/ed8c4c/32.png) [@Dave\_Peticolas](https://forum.ansible.com/u/Dave_Peticolas)\
**Post date:** [August 25, 2012, 3:29am UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/2 "2012-08-25T03:29:19Z")

</div>

2012/8/24 Michael DeHaan \<[michael.dehaan@gmail.com](mailto:michael.dehaan@gmail.com)\>

> The question about how variables override each other has come up a few  
> times in the last few days.
> 
> As a result, I added documentation on this to the “Advanced Playbooks”  
> chapter, and am including that here so folks can see it.
> 
> There are no changes in current behavior, this is just documenting how  
> things work. It’s kind of amusing because I myself didn’t know the  
> order until I looked it up – I mostly didn’t do a lot of attempts to  
> override variables and mostly rely on group and host variables when I  
> need one to override the other – though in the end, it works pretty  
> well logically.
> 
> If you define a variable in a playbook, you have total assurance that  
> value will be used.
> 
> If you want to play with overrides and such, group and host variables  
> are the places you do that, with the variables for the ‘all’ group  
> essentially being a global bucket that is optimal for defaults.
> 
> == START ==
> 
> You have already learned about inventory host and group variables,  
> ‘vars’, and ‘vars\_files’.
> 
> If a variable name is defined in more than one place with the same  
> name, priority is as follows to determine which place sets the value  
> of the variable.
> 
> Variables loaded from YAML files mentioned in ‘vars\_files’ in a playbook.  
> ‘vars’ as defined in the playbook.  
> facts, whether built in or custom, or variables assigned from the  
> ‘register’ keyword.  
> variables passed to parameterized task include statements.  
> Host variables from inventory.  
> Group variables from inventory, in order of least specific group  
> to most specific.
> 
> Therefore, if you want to set a default value for something you wish  
> to override somewhere else, the best place to set such a default is in  
> a group variable.
> 
> == END ==

Thanks for writing that up. A few questions and comments:

1. I assume the list is in order of decreasing priority, but I think it  
would be good to state the explicitly.

2. If so, and if the least-specific group (the ‘all’ group?) has the  
least priority, then I think the last item should read ‘in order of  
most specific to least specific’, as that would put the least-specific  
group at the very end of the list.

3. I’m not entirely sure how to evaluate group specificity. If I have the  
following groups:

[group-a]  
server-1  
server-2

[group-b]  
server-2  
server-3

[group-c:children]  
group-a  
group-b

What is the order of specificity? Why is group-a more or less specific  
than group-b (note server2 is in both).

thanks,  
dave

---

<div class="post-metadata">

**Author:** ![Michael\_DeHaan](https://avatars.discourse-cdn.com/v4/letter/m/c4cdca/32.png) [@Michael\_DeHaan](https://forum.ansible.com/u/Michael_DeHaan)\
**Post date:** [August 25, 2012, 12:55pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/3 "2012-08-25T12:55:54Z")

</div>

> &nbsp;&nbsp;&nbsp;&nbsp;[group-a]  
> &nbsp;&nbsp;&nbsp;&nbsp;server-1  
> &nbsp;&nbsp;&nbsp;&nbsp;server-2
> 
> &nbsp;&nbsp;&nbsp;&nbsp;[group-b]  
> &nbsp;&nbsp;&nbsp;&nbsp;server-2  
> &nbsp;&nbsp;&nbsp;&nbsp;server-3
> 
> &nbsp;&nbsp;&nbsp;&nbsp;[group-c:children]  
> &nbsp;&nbsp;&nbsp;&nbsp;group-a  
> &nbsp;&nbsp;&nbsp;&nbsp;group-b
> 
> &nbsp;&nbsp;&nbsp;&nbsp;What is the order of specificity? Why is group-a more or less specific  
> &nbsp;&nbsp;&nbsp;&nbsp;than group-b (note server2 is in both).

It goes in depth order, so A vs B would be undefined. Also, if you  
are seeking to do this, I think you're probably over-thinking the  
variable modelling problem and should  
simplify -- keep it simple and you won't need to think about it.

---

<div class="post-metadata">

**Author:** ![Dave\_Peticolas](https://avatars.discourse-cdn.com/v4/letter/d/ed8c4c/32.png) [@Dave\_Peticolas](https://forum.ansible.com/u/Dave_Peticolas)\
**Post date:** [August 25, 2012, 5:07pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/4 "2012-08-25T17:07:37Z")

</div>

2012/8/25 Michael DeHaan \<[michael.dehaan@gmail.com](mailto:michael.dehaan@gmail.com)\>

> > [group-a]  
> > server-1  
> > server-2
> > 
> > [group-b]  
> > server-2  
> > server-3
> > 
> > [group-c:children]  
> > group-a  
> > group-b
> > 
> > What is the order of specificity? Why is group-a more or less specific  
> > than group-b (note server2 is in both).
> 
> It goes in depth order, so A vs B would be undefined. Also, if you  
> are seeking to do this, I think you’re probably over-thinking the  
> variable modelling problem and should  
> simplify – keep it simple and you won’t need to think about it.

I am not seeking to do that, I am seeking to understand how variable  
precedence works so the (hopefully simple!) variables I do define end  
up with the values I think they are going to have.

Group depth is a much more direct way of expressing that rule than  
‘specificity’. However, I wonder if you would consider an even simpler  
rule instead:

Group precedence is their order in the hosts file, first group wins.

That would encompass the current ‘group depth’ rule (you have to define  
child groups before you can define parents) but is easier to understand,  
easier to predict, and has no undefined cases.

dave

---

<div class="post-metadata">

**Author:** ![Michael\_DeHaan](https://avatars.discourse-cdn.com/v4/letter/m/c4cdca/32.png) [@Michael\_DeHaan](https://forum.ansible.com/u/Michael_DeHaan)\
**Post date:** [August 25, 2012, 5:14pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/5 "2012-08-25T17:14:18Z")

</div>

> Group depth is a much more direct way of expressing that rule than  
> 'specificity'. However, I wonder if you would consider an even simpler  
> rule instead:
> 
> &nbsp;&nbsp;Group precedence is their order in the hosts file, first group wins.

No, I don't find that simpler or more obvious in the least.

---

<div class="post-metadata">

**Author:** ![Dave\_Peticolas](https://avatars.discourse-cdn.com/v4/letter/d/ed8c4c/32.png) [@Dave\_Peticolas](https://forum.ansible.com/u/Dave_Peticolas)\
**Post date:** [August 25, 2012, 5:21pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/6 "2012-08-25T17:21:06Z")

</div>

2012/8/25 Michael DeHaan \<[michael.dehaan@gmail.com](mailto:michael.dehaan@gmail.com)\>

> > Group depth is a much more direct way of expressing that rule than  
> > ‘specificity’. However, I wonder if you would consider an even simpler  
> > rule instead:
> > 
> > Group precedence is their order in the hosts file, first group wins.
> 
> No, I don’t find that simpler or more obvious in the least.

Well, fair enough. Would you consider updating the documentation  
wording to mention group depth? I don’t find ‘specificity’ to be at all  
obvious.

dave

---

<div class="post-metadata">

**Author:** ![Michael\_DeHaan](https://avatars.discourse-cdn.com/v4/letter/m/c4cdca/32.png) [@Michael\_DeHaan](https://forum.ansible.com/u/Michael_DeHaan)\
**Post date:** [August 25, 2012, 9:48pm UTC](https://forum.ansible.com/t/understanding-variable-precedence/11827/7 "2012-08-25T21:48:28Z")

</div>

maybe.
