Building ansible inventory with 1 IP multiple host name - ansible

Can i know, is this possible to have 1 IP with multiplle inventory host name as below
[server_name_1]
[server_name_2]
192.168.172.22

The host file entry that you have mentioned over here, When you will run it there will be no errors but:-
The Following entry when you will use the hostname in your playbook like this
---
- hosts: server_name_1
PLAY [server_name_1]
***************
skipping: no hosts matched
It will produce no-host match as there is no IP associated with that Block. If you use the second one with proper key and access will work fine. But the above host file is syntactically correct.

Related

ansible-playbook:: how to play on other host than configured

I am trying to play a yml on other host than configured, using -l option.. but skipping: no hosts matched .
The scenario is where a host associated playbook is needed to be exceptionally used for some other host. (and for safety reasons, the playbook cannot have hosts:all and be left to the admin to limit the target(s))
What is the correct way to do this (if there is any)?
L.E. So, in the end, the answer of #mdaniel gave me the idea o a bash wrapper that creates a temp yml where the host: field is replaced with the argument.. it's not pretty but it works. (same works for a dynamical generation of a playbook from a series of tasks)
and the proper ansible way to do it i just found it here:
https://stackoverflow.com/a/18195217/624734
What is the correct way to do this?
Use all as the target of the playbook, and then constrain the hosts it applies to via the inventory, or the --limit that you mentioned
- hosts: all
# and now the rest of your playbook
You can try the below approach if you want to restrict hosts:all in your ansible script.
- hosts: "{{ host_group }}"
# Rest of your playbook
And you can have a specific group in your hosts file which you can use for testing.
For example,
[test]
192.168.1.1 # Test host
# Rest of your inventory file
And trigger the ansible playbook in the following order,
ansible-playbook -i hosts main.yml -e host_group="test"

Ansible: Connect to Nodes without DNS or /etc/hosts" resolution

I have a Dynamic Inventory Script which outputs the following.
"NODE_A": {
"inventory_hostname": "10.0.2.6",
"inventory_lparname": "NODE_A"
}
The Nodes are not resolvable via DNS or something as this Network is some kind of isolated "Management" LAN.
Until now i had a Play running which modifies the local /etc/hosts File to enable Name Resolution.
As the Ansible Controller is going to move to an foreign Machine, this is not possible anymore.
So the big question is how to proceed. How do i instruct Ansible to connect to the IP Adress instead of the Hostname, repectively can i use "inventory_hostname" instead of "ansible_hostname" as Connection String, but keep the Hostname displayed in the Play Recap?
How do i instruct Ansible to connect to the IP Adress instead of the Hostname, repectively can i use "inventory_hostname" instead of "ansible_hostname" as Connection String, but keep the Hostname displayed in the Play Recap?
The normal way you handle this is to set the inventory hostname to the "friendly" name, and then set ansible_hostname to the ip address. That is, if your inventory script reports a host named "host0", then when called with --host host0 it should produce:
{
"inventory_hostname": "host0",
"ansible_host": "10.0.2.6",
}
You will see the name host0 in playbook output, but ansible will use the ip address for connections.
An option would be to extend the Dynamic Inventory Scrip to add or replace nodes in an inventory directory. For example in INI format
NODE_A ansible_host=10.0.2.6

Making a hosts file group into an input in Ansible playbook

I have an ansible playbook that calls an API. I have a delegate_to: localhost.
I want to run my playbook "against" every host in a group Linux.
I want the API call to do 2 things.
I want it to run once for every host in the Linux group
For every run, it should have a different host IP/hostname as the input
linux looks like:
[linux]
10.234.0.13
10.234.0.12
I run my like this: ansible-playbook -i linux my_playbook
How do I make the inventory group an input?
when ansible executes on the remote host it collects some meta data of the hosts. One of the meta data is ip address. The meta data is called ansible facts. There is an ansible fact to get the ip address
ansible_default_ipv4.address

Ansible get hostname as defined in inventory

In my inventory I define hosts like this:
[server1]
141.151.176.223
I am looking for a variable which keeps the server1 name, as I am using it to define server hostname.
inventory_hostname is set to 141.151.176.223
ansible_hostname as well as inventory_hostname_short is set to 148.
To workaround this problem I am setting my own variable like this:
[server1]
141.151.176.223 hostname=server1
but I am not satisfied with this approach.
Any ideas?
Explanation
If the inventory file was defined this way:
[server1_group]
server1 ansible_host=141.151.176.223
Then you can access:
server1 with the inventory_hostname fact;
141.151.176.223 with the ansible_host fact;
server1_group with group_names|first (group_names fact contains a list of all groups server belongs to, first selects the first element from that list).
Regardless of the above, ansible_hostname fact contains the host name as defined on the host itself (the value is set during facts gathering).
Solution
You should use a standard ansible_host declaration to point to the target's IP address and set the inventory hostname to however you want to refer to the server in Ansible playbooks.
In particular you can skip groups definition altogether and define just:
server1 ansible_host=141.151.176.223
The [server1] declaration is the name of a group, not a host (even if you only assign a single host to that group).
As ansible allows a host to be placed in multiple groups, you can only get the names as an array: http://docs.ansible.com/ansible/latest/playbooks_variables.html#magic-variables-and-how-to-access-information-about-other-hosts
So I think the workaround that you found is the way to go, unless you can use real host names instead of IP addresses (using DNS or just static hosts file).

Run Ansible playbook without inventory

Consider if I want to check something quickly. Something that doesn't really need connecting to a host (to check how ansible itself works, like, including of handlers or something). Or localhost will do. I'd probably give up on this, but man page says:
-i PATH, --inventory=PATH
The PATH to the inventory, which defaults to /etc/ansible/hosts. Alternatively, you can use a comma-separated
list of hosts or a single host with a trailing comma host,.
And when I run ansible-playbook without inventory, it says:
[WARNING]: provided hosts list is empty, only localhost is available
Is there an easy way to run playbook against no host, or probably localhost?
Prerequisites. You need to have ssh server running on the host (ssh localhost should let you in).
Then if you want to use password authentication (do note the trailing comma):
$ ansible-playbook playbook.yml -i localhost, -k
In this case you also need sshpass.
In case of public key authentication:
$ ansible-playbook playbook.yml -i localhost,
And the test playbook, to get you started:
- hosts: all
tasks:
- debug: msg=test
You need to have a comma in the localhost, option argument, because otherwise it would be treated as a path to an inventory. The inventory plugin responsible for parsing the value can be found here.
You can define a default inventory with only localhost
See it is explained here:
https://docs.ansible.com/ansible/latest/reference_appendices/config.html#the-configuration-file
And in your playbook add use this
- hosts: all
connection: local
tasks:
- debug: msg=test
It will use local connection so no SSH is required (thus it doesn't expose your machine). It might be quicker unless you need to troubleshoot a ssh issue.
Also for quicker feedback loop you can use: gather_facts: no you already know your target.

Resources