define variables for multiple hosts in one file inside host_vars

Let’s say I have two groups of devices to configure, eos-group and junos-group.

Let’s focus on junos-group.
I have 10 devices in the junos-group.
Each device will be configured with a mgmt ip, hostname, interface, routes …etc

Inside of /etc/ansible/host_vars/, I could create different files for each host: hostname1.yaml, hostname2.yaml …
However, this doesn’t. scale, does it?

Can I just create one file (lets call it all_junos_hosts.yaml) inside /etc/ansible/host_vars/, and inside of t his single file, I’ll use hierarchical structure to define variables for different hosts?
E.g: my all_junos_hosts.yaml file will look like this:

10.10.10.10:
hostname: hostname1
data_nexthop: 10.10.10.1
interfaces:
mgmt_interface:
name: em0
ip: 10.10.10.10:

12.12.12.12:
hostname: hostname2
data_nexthop: 12.12.12.1
interfaces:
mgmt_interface:
name: em0
ip: 12.12.12.12

I read somewhere that if I create a file called all_junos_hosts.yaml inside of /etc/ansible/host_vars/, ansible will think there is a host called all_junos_hosts.yaml.
How do I get around this?

Basically all I want to do is, in my template, I’ll do something like set interfaces management "{{ reference for mgmt interface for this host }}" … etc

First off, rename your groups to NOT have a hyphen. This is critical.
Then, use group_var/junos_group/ and define the common stuff below there.
Same for the group_vars/eos_group/

it's all laid out in
https://docs.ansible.com/ansible/latest/user_guide/intro_inventory.html

Dick

@Dick … In fact, I have group_vars/all.yaml and in there I have stuff like credentials and username/password, since this is common for all devices
I can create group_vars/eos_group.yaml and group_vars/junos_group.yaml. However, this still does not solve the issue of having multiple variables for the multiple hosts in the same file.

Okay let’s say I now have group_vars/junos_group.yaml. Inside this file I have the defined variables for 10 different hosts.

10.10.10.10:
hostname: hostname1
data_nexthop: 10.10.10.1
interfaces:
mgmt_interface:
name: em0
ip: 10.10.10.10:

12.12.12.12:
hostname: hostname2
data_nexthop: 12.12.12.1
interfaces:
mgmt_interface:
name: em0
ip: 12.12.12.12

In my playbook, I can reference value em0 with “{{ group_vars[inventory_hostname][‘interfaces’][‘mgmt_interface’][‘name’] }}”

Is this correct?
Thanks

No. You are mixing up groups and hosts (and probably the inventory as well).
All variables under group_vars are meant to be specific to groups only
- not hosts.
Hosts specific variables go under their respective host_vars files.

Host and group specific variables can be set in the inventory,
group_vars, and host_vars.
Setting stuff in the inventory is usually done for very simple structures.
Given that your host specific data is already a nested dictionary, I
would not use the inventory for that.

Your example indicates that the entire 'interfaces' dictionary is, in
fact, not variable, it's the same for each host. You can add this to
the group_vars in this case:

  interfaces:
    mgmt_interface:
      name: em0
      ip: "{{ ansible_hostname }}"

If your data is in fact different, please post a more accurate example.

That’s a nice suggestion and I agree it will solve the problem to an extent.
I only showed a simple interface config here to keep things simple but the host specific configs is much more than just the mgmt em0 ip address. Let me give you a more realistic example:

10.10.10.10:
hostname: hostname1
data_nexthop: 100.12.1.7
interfaces:
mgmt_interface:
name: em0
ip: 10.10.10.10
subnet: 31
data_interface:
name: et-0/0/3
ip: 100.12.1.6
subnet: 31
tor_name: seattle_router_01

See the data_interface is going to be different for each host, the data_interface’s ip, next_hop and it’s tor_name are all specific to each host.

Would you recommend I put all of these host_specific values in host file then? I mean the /etc/ansible/hosts?

Creating a yaml file for each host under /etc/ansible/host_vars will be a bit too much.

What do you mean by "it will be a bit too much"?
I'm not sure what problem is?

As I said before, the host_vars directory is meant to house (at least)
one file per host.
That piece of YAML you posted is NOT going to work inside host_vars
(but see below).

The other way to define per-host variables is the inventory.
What you have now already is almost exactly what a (YAML based)
inventory file looks like.
That can be a single file, so if that is what you are after (I'm
deducting this from your statement about one file per host being "a
bit too much" - but correct me if I'm wrong), then problem solved.

No matter how you look at it, you have a large number of hosts, each
having an inherently complex (i.e. nested) set of specific host
variables.

Dick what I meant by “it will be a bit too much” is that I have over 100 hosts, and it will only increase. Do I really want to create a file for each of these hosts in the host_vars directory?
This does not seem like it will scale well. 1000 hosts means 1000 files in host_vars directory.

Considering I have over 100 hosts, each with it’s own host-specific variables/values. And I need to use these variables/values in my jinja template to render a config for each host.
You being the expert here, how do you think I should approach this?

  • Create yaml files for each of the 100 hosts in /etc/ansible/host_vars. ( host_vars/host1, host2 …host100)
  • Inside of my hosts file in /etc/ansible/hosts.yaml/ini, for each host in hosts, define variables/values for each host (I could use the hosts.ini too)
  • or you’re thinking of something else? Or one the two above will work some tweaking?

Thanks for the support. My head hurts now.

^^
This is the preferred choice in your case. To be clear, this is the
"defining host variable in the inventory" approach.
And because those variables are nested/complex, it's probably best to
use a single YAML style inventory file.
This is what it would be looking like:

dnmvisser@NUC8i5BEK ~$ cat inventory.yml

Dick what I meant by "it will be a bit too much" is that I have over 100 hosts, and it will only increase. Do I really
want to create a file for each of these hosts in the host_vars directory?
This does not seem like it will scale well. 1000 hosts means 1000 files in host_vars directory.

Considering I have over 100 hosts, each with it's own host-specific variables/values. And I need to use these
variables/values in my jinja template to render a config for each host.
You being the expert here, how do you think I should approach this?
- Create yaml files for each of the 100 hosts in /etc/ansible/host_vars. ( host_vars/host1, host2 ...host100)
- Inside of my hosts file in /etc/ansible/hosts.yaml/ini, for each host in hosts, define variables/values for each host
(I could use the hosts.ini too)
- or you're thinking of something else? Or one the two above will work some tweaking?

Thanks for the support. My head hurts now.

Lots of files in host_vars is probably not the solution, but otherwise you need to come up with a logic how this
host values are determined. If you have such a logic, a dynamic inventory might be helpful.

Regards
          Racke

Thanks for working with me Dick.
I’ll I’ll follow your suggestion and report back.

Appreciated.

Racke,
Unfortunately there is no good pattern here for me to leverage. I’ll have to hardcode a lot of host-specific values for each host in an inventory file.
And the template could pick up values from there.