Using Ansible Facts to get devices information

Ansible facts, i.e. when i run ansible all -m setup I get all the basic information like the interfaces, IP etc, But i am really interested in also getting disk/partition information and devices attached, Like the information with fdisk and hdparm/smartctl will give.

Is there a way i can get those from facts ? If not what would be the right vehicle ? Modify setup.py to get the details needed ?

Modifying setup will work, but take into account that this is relied on by default for all plays. I had this at one point (for freebsd), but didn’t need it any more and setup has changed a lot since then.

You can also create your own module that adds custom facts.

Brian Coca

I just remembered, check the setup module docs, it uses a couple of popular system info gathering utilities if they are installed on the target, they might already get the mount info.

Brian Coca

It looks like facter/ohai needs ruby installed on remote machines, I wanted something pure python and with least dependencies, So tried to create a module.

newbie alert ! How to get this module (attached) reviewed /get help ?

I tried to port the disk-info python script to a Ansible module (from little i understand- started reading about Ansible yesterday). I have attached the module here. I would appreciate if i can get some comments on how to improve it , so it follows all the ansible conventions.

The output looks like this:

{‘Devices’: {‘sda’: {‘vendor’: ‘ATA’, ‘sectors’: ‘976773168’, ‘sector size(bytes)’: ‘512’, ‘disk type’: ‘Spinning disk’, ‘host’: ‘SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)’, ‘sda2’: {‘holders’: {0: ‘VolGroup00-LogVol01’, 1: ‘VolGroup00-LogVol00’}, ‘sectors’: ‘975747072’, ‘start sector’: ‘1026048’, ‘size’: ‘465.27GiB’}, ‘removable’: ‘No’, ‘sda1’: {‘sectors’: ‘1024000’, ‘start sector’: ‘2048’, ‘size’: ‘500.00MiB’}, ‘support discard’: ‘No’, ‘model’: ‘ST500DM002-1BC14’, ‘size’: ‘465.76GiB’}, ‘sdb’: {‘vendor’: ‘ATA’, ‘sectors’: ‘395093371’, ‘sector size(bytes)’: ‘512’, ‘disk type’: ‘SSD’, ‘host’: ‘SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)’, ‘removable’: ‘No’, ‘support discard’: ‘Yes’, ‘model’: ‘SAMSUNG SSD 830’, ‘size’: ‘188.40GiB’}, ‘sdc’: {‘vendor’: ‘ATA’, ‘sectors’: ‘395093371’, ‘sector size(bytes)’: ‘512’, ‘disk type’: ‘SSD’, ‘host’: ‘SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)’, ‘removable’: ‘No’, ‘support discard’: ‘Yes’, ‘model’: ‘SAMSUNG SSD 830’, ‘size’: ‘188.40GiB’}}}

(to get the above result in main of get_devices module, i commented out ansible related stuff and ran as a standalone python script which just printed output of get_devices(module))

Regards,–
Kavin K

(attachments)

get_devices (9.11 KB)

I guess cannot attach file: uploaded it here:

https://www.filepicker.io/api/file/egn0MijfQ1ISBD8wxALQ

It looks like facter/ohai needs ruby installed on remote machines, I
wanted something pure python and with least dependencies, So tried to
create a module.

newbie alert ! How to get this module (attached) reviewed /get help ?

The way I understand it is that you put your module data in a dict named
ansible_facts and return it , like this:

    ansible_facts['riak_primary_node'] = host_list[0]
    ansible_facts['riak_last_node'] = host_list[-1]
    ansible_facts['riak_node_count'] = len(host_list)
    changed = True

    result = {"changed": changed,
              "ansible_facts": ansible_facts }
    module.exit_json(**result)

Then from your module you can directly access your custom facts like:

$riak_primary_node
$riak_node_count

etc.

This is all documented http://ansible.cc/docs/moduledev.htm under "Module
Provided 'Facts'.

- James

This is super minor, but I figured I'd share... there's no need to
return a 'changed' attribute in a facts module.

A changed = True/False only is really useful if you have a 'notify'
hanging off of the task and the module makes changes to the underlying
system.

It implies that the module has actually /changed/ the underlying
system, so you wouldn't want to return it unless that were actually
the case.

--Michael

2 small changes, added a path to lspci and made it non critical if it
isn't isntalled.

    pcidata = None
    try:
        p = Popen(["/usr/sbin/lspci"], stdout=PIPE)
        err = p.wait()
        if err:
            print "Error running lspci"
        else:
            pcidata = p.stdout.read()
    except OSError:
        pass # no lspci

works nicely for me now

Thanks for all the feedback, On my Centos 6.3 machine lspci is located in /sbin/lspci
So i changed it to:

pcidata = None
try:
try:
p = Popen([“/sbin/lspci”], stdout=PIPE)
except:
try:
p = Popen([“/usr/sbin/lspci”], stdout=PIPE)
except:
p = Popen([“lspci”], stdout=PIPE)
err = p.wait()
if err:
print “Error running lspci”
else:
pcidata = p.stdout.read()
except OSError, e:
module.fail_json( msg=“lspci failed %s” % e) # no lspci

https://www.filepicker.io/api/file/nsajpMMqSu2AIjPGC3lA

This is the modified code based on the feedback received, Let me know if i can make it better .

Out put:

s2 | success >> {
“ansible_facts”: {
“device_details”: {
“sda”: {
“disk type”: “Spinning disk”,
“host”: “SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)”,
“model”: “ST500DM002-1BC14”,
“removable”: “No”,
“sda1”: {
“sectors”: “1024000”,
“size”: “500.00MiB”,
“start sector”: “2048”
},
“sda2”: {
“holders”: [
“VolGroup00-LogVol01”,
“VolGroup00-LogVol00”
],
“sectors”: “975747072”,
“size”: “465.27GiB”,
“start sector”: “1026048”
},
“sector size(bytes)”: “512”,
“sectors”: “976773168”,
“size”: “465.76GiB”,
“support discard”: “No”,
“vendor”: “ATA”
},
“sdb”: {
“disk type”: “SSD”,
“host”: “SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)”,
“model”: “SAMSUNG SSD 830”,
“removable”: “No”,
“sector size(bytes)”: “512”,
“sectors”: “395093371”,
“size”: “188.40GiB”,
“support discard”: “Yes”,
“vendor”: “ATA”
},
“sdc”: {
“disk type”: “SSD”,
“host”: “SATA controller: Intel Corporation 6 Series/C200 Series Chipset Family SATA AHCI Controller (rev 05)”,
“model”: “SAMSUNG SSD 830”,
“removable”: “No”,
“sector size(bytes)”: “512”,
“sectors”: “395093371”,
“size”: “188.40GiB”,
“support discard”: “Yes”,
“vendor”: “ATA”
}
},
“devices”: [
“sda”,
“sdb”,
“sdc”
]
},
“changed”: false
}

Regards,–
Kavin Kankeshwar

Small request.

For those sharing larger pieces of files on this mailing list, I'd
recommend using something like github's gist versus a file download
site like filepicker.

It's much easier to tell what you are looking at before you download
something potentially unsafe.

Pastebin is somewhat less tolerable as content tends to expire.

A small patch that puts partitions in their own key and also adds
mount information

--- Downloads/get_devices 2012-12-29 17:36:50.162819361 -0500
+++ get_devices 2012-12-29 17:37:07.014825267 -0500
@@ -278,6 +278,18 @@
     a_devices= {}
     device_names=
     dd={}

Thanks for all the help, Sorry about sending files to the group…

https://github.com/kavink/ansible/blob/devel/library/get_devices

Now I also get the scheduler-mode for the devices.

Regards,–
Kavin Kankeshwar

You may find get_bin_path() in module_common.py useful when searching for the full path to lcpsi:

https://github.com/ansible/ansible/blob/devel/lib/ansible/module_common.py#L560

i had a minor version of this hacked into setup, should I attempt to
put this version in (under linux facts)? I would also add a freeBSD
version

i had a minor version of this hacked into setup, should I attempt to
put this version in (under linux facts)? I would also add a freeBSD
version

Sounds good!

--Michael