Reputation: 89
I need to go over 100 machines and get the total size of /var. Then aggregate the space for all machines and print it. I made several tries to get my data without success and I'm seeking for help.
I am not sure that using facts is the right way and there might be other modules I'm not aware off that can do the job. Here what I have tried so far.
---
- hosts: servers
remote_user: ansible
become: true
gather_facts: no
tasks:
- name: Initialize an empty list for our strings
set_fact:
my_strings: []
- name: fetching
shell: du -sh /var
register: var
- name: Append string to list
set_fact:
my_strings: "{{ my_strings + [ var.stdout ] }}"
- name: print output
debug:
msg: "-> {{ my_strings }}"
Upvotes: 0
Views: 2252
Reputation: 44615
You can use facts but you are using them the wrong way. What you have to understand is that:
So adding disk spaces as list elements like you are trying to do will basically add nothing but the individual calculated space in a single element list for each machine.
What you can do is collect individual facts on each machine and then manipulate them, even sum them if they have a compatible type... This is possible using the magic variable hostvars
and a few filters you will have to get familiar with going through the following documentations:
Here is an example playbook that you can run without having to connect anywhere. I created 3 fake hosts connecting to my local machine just for that purpose. Replace/adapt with your own inventory and you should be fine. I tried to demonstrate a few data manipulation techniques in ansible. You can combine those differently and use others to suit your exact needs. I hope it will help to clarify the problem anyway.
This is my example inventories/demo/hosts.yml
---
all:
vars:
ansible_connection: local
ansible_python_interpreter: /usr/bin/python3
children:
servers:
hosts:
demo1:
demo2:
demo3:
The example var_size.yml
playbook:
---
- name: Get /var size on all servers hosts
hosts: servers
gather_facts: false
tasks:
- name: Fetching /var size on hosts
command: du -s /var
register: du_var
become: true
changed_when: false
# This is absolutely needed as registers don't survive current play
# See next play on localhost only
- name: Store actual size for hosts in a fact
vars:
size_regex: >-
^(\d+)\s*/var
replace: >-
\g<1>
set_fact:
var_size_bytes: "{{ du_var.stdout | regex_replace(size_regex, replace) }}"
# As a first example, demonstrate we can simply display sizes
# with the natural play host loop
- name: Show human readable size of /var on each host
debug:
msg: "/var size is: {{ var_size_bytes | int | human_readable }}"
# Now we can work on consolidating
- name: Consolidate data we gathered
hosts: localhost
gather_facts: false
tasks:
- name: Create a dict of sizes extracting all relevant hostvars
# This fact is set on localhost as this is the only play target
set_fact:
var_sizes_host_dict: "{{ groups['servers'] | map('extract', hostvars) | items2dict(key_name='inventory_hostname', value_name='var_size_bytes') }}"
- name: Show the raw dict with bytes sizes
debug:
var: var_sizes_host_dict
- name: Display sizes for all hosts in human readable format
vars:
hostnames: "{{ var_sizes_host_dict.keys() }}"
hr_sizes: "{{ var_sizes_host_dict.values() | map('int') | map('human_readable') }}"
var_sizes_host_dict_hr: "{{ hostnames | zip(hr_sizes) | items2dict(key_name=0, value_name=1) }}"
debug:
msg: "{{ var_sizes_host_dict_hr }}"
- name: Sum all /var sizes
vars:
host_number: "{{ var_sizes_host_dict | length }}"
total_space: "{{ var_sizes_host_dict.values() | map('int') | sum }}"
raw_message: |-
The total number of host is: {{ host_number }}
The total /var space used is: {{ total_space | int | human_readable }}
debug:
msg: "{{ raw_message.split('\n') }}"
Which gives:
$ ansible-playbook -i inventories/demo var_size.yml
PLAY [Get /var size on all demo hosts] *************************************************************************************************************************************************************************************************
TASK [Fetching /var size on hosts] *****************************************************************************************************************************************************************************************************
ok: [demo3]
ok: [demo1]
ok: [demo2]
TASK [Store actual size for hosts in a fact] *******************************************************************************************************************************************************************************************
ok: [demo2]
ok: [demo1]
ok: [demo3]
TASK [Show human readable size of /var on each host] ***********************************************************************************************************************************************************************************
ok: [demo1] => {
"msg": "/var size is: 4.31 MB"
}
ok: [demo3] => {
"msg": "/var size is: 4.31 MB"
}
ok: [demo2] => {
"msg": "/var size is: 4.31 MB"
}
PLAY [Consolidate data we gathered] ****************************************************************************************************************************************************************************************************
TASK [Create a dict of sizes extracting all relevant hostvars] *************************************************************************************************************************************************************************
ok: [localhost]
TASK [Show the raw dict with bytes sizes] **********************************************************************************************************************************************************************************************
ok: [localhost] => {
"var_sizes_host_dict": {
"demo1": "4518993",
"demo2": "4518993",
"demo3": "4518993"
}
}
TASK [Display sizes for all hosts in human readable format] ****************************************************************************************************************************************************************************
ok: [localhost] => {
"msg": {
"demo1": "4.31 MB",
"demo2": "4.31 MB",
"demo3": "4.31 MB"
}
}
TASK [Sum all /var sizes] **************************************************************************************************************************************************************************************************************
ok: [localhost] => {
"msg": [
"The total number of host is: 3",
"The total /var space used is: 12.93 MB"
]
}
PLAY RECAP *****************************************************************************************************************************************************************************************************************************
demo1 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
demo2 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
demo3 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
localhost : ok=4 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
Upvotes: 1