From 984777b3d022ff4bb4d5eda57efde52b1fb93875 Mon Sep 17 00:00:00 2001 From: Simon Dodsley Date: Mon, 11 Feb 2019 18:34:22 -0500 Subject: [PATCH] Update FlashArray facts to get new information (#51550) --- .../storage/purestorage/purefa_facts.py | 86 +++++++++++++++++-- 1 file changed, 77 insertions(+), 9 deletions(-) diff --git a/lib/ansible/modules/storage/purestorage/purefa_facts.py b/lib/ansible/modules/storage/purestorage/purefa_facts.py index f5be2498048..970409452bd 100644 --- a/lib/ansible/modules/storage/purestorage/purefa_facts.py +++ b/lib/ansible/modules/storage/purestorage/purefa_facts.py @@ -30,7 +30,7 @@ options: - When supplied, this argument will define the facts to be collected. Possible values for this include all, minimum, config, performance, capacity, network, subnet, interfaces, hgroups, pgroups, hosts, - volumes, snapshots, pods, vgroups and offload. + volumes, snapshots, pods, vgroups, offload and apps. required: false default: minimum extends_documentation_fragment: @@ -335,6 +335,8 @@ from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.pure import get_system, purefa_argument_spec +S3_REQUIRED_API_VERSION = '1.16' +LATENCY_REQUIRED_API_VERSION = '1.16' AC_REQUIRED_API_VERSION = '1.14' CAP_REQUIRED_API_VERSION = '1.6' SAN_REQUIRED_API_VERSION = '1.10' @@ -348,10 +350,19 @@ def generate_default_dict(array): default_facts['volume_groups'] = len(array.list_vgroups()) default_facts['connected_arrays'] = len(array.list_array_connections()) default_facts['pods'] = len(array.list_pods()) + default_facts['connection_key'] = array.get(connection_key=True)['connection_key'] hosts = array.list_hosts() snaps = array.list_volumes(snap=True, pending=True) pgroups = array.list_pgroups(pending=True) hgroups = array.list_hgroups() + # Old FA arrays only report model from the primary controller + ct0_model = array.get_hardware('CT0')['model'] + if ct0_model: + model = ct0_model + else: + ct1_model = array.get_hardware('CT1')['model'] + model = ct1_model + default_facts['array_model'] = model default_facts['array_name'] = defaults['array_name'] default_facts['purity_version'] = defaults['version'] default_facts['hosts'] = len(hosts) @@ -363,6 +374,9 @@ def generate_default_dict(array): def generate_perf_dict(array): perf_facts = {} + api_version = array._list_available_rest_versions() + if LATENCY_REQUIRED_API_VERSION in api_version: + latency_info = array.get(action='monitor', latency=True)[0] perf_info = array.get(action='monitor')[0] # IOPS perf_facts['writes_per_sec'] = perf_info['writes_per_sec'] @@ -373,10 +387,14 @@ def generate_perf_dict(array): perf_facts['output_per_sec'] = perf_info['output_per_sec'] # Latency - api_version = array._list_available_rest_versions() - if SAN_REQUIRED_API_VERSION in api_version: - perf_facts['san_usec_per_read_op'] = perf_info['san_usec_per_read_op'] - perf_facts['san_usec_per_write_op'] = perf_info['san_usec_per_write_op'] + if LATENCY_REQUIRED_API_VERSION in api_version: + perf_facts['san_usec_per_read_op'] = latency_info['san_usec_per_read_op'] + perf_facts['san_usec_per_write_op'] = latency_info['san_usec_per_write_op'] + perf_facts['queue_usec_per_read_op'] = latency_info['queue_usec_per_read_op'] + perf_facts['queue_usec_per_write_op'] = latency_info['queue_usec_per_write_op'] + perf_facts['qos_rate_limit_usec_per_read_op'] = latency_info['qos_rate_limit_usec_per_read_op'] + perf_facts['qos_rate_limit_usec_per_write_op'] = latency_info['qos_rate_limit_usec_per_write_op'] + perf_facts['local_queue_usec_per_op'] = perf_info['local_queue_usec_per_op'] perf_facts['usec_per_read_op'] = perf_info['usec_per_read_op'] perf_facts['usec_per_write_op'] = perf_info['usec_per_write_op'] perf_facts['queue_depth'] = perf_info['queue_depth'] @@ -398,6 +416,20 @@ def generate_config_dict(array): config_facts['ntp'] = array.get(ntpserver=True)['ntpserver'] # SYSLOG config_facts['syslog'] = array.get(syslogserver=True)['syslogserver'] + # Phonehome + config_facts['phonehome'] = array.get(phonehome=True)['phonehome'] + # Proxy + config_facts['proxy'] = array.get(proxy=True)['proxy'] + # Relay Host + config_facts['relayhost'] = array.get(relayhost=True)['relayhost'] + # Sender Domain + config_facts['senderdomain'] = array.get(senderdomain=True)['senderdomain'] + # SYSLOG + config_facts['syslog'] = array.get(syslogserver=True)['syslogserver'] + # Idle Timeout + config_facts['idle_timeout'] = array.get(idle_timeout=True)['idle_timeout'] + # SCSI Timeout + config_facts['scsi_timeout'] = array.get(scsi_timeout=True)['scsi_timeout'] # SSL config_facts['ssl_certs'] = array.get_certificate() return config_facts @@ -525,6 +557,8 @@ def generate_host_dict(array): 'hgroup': hosts[host]['hgroup'], 'iqn': hosts[host]['iqn'], 'wwn': hosts[host]['wwn'], + 'personality': array.get_host(hostname, + personality=True)['personality'] } return host_facts @@ -555,10 +589,24 @@ def generate_pods_dict(array): 'source': pods[pod]['source'], 'arrays': pods[pod]['arrays'], } - return pods_facts +def generate_apps_dict(array): + apps_facts = {} + api_version = array._list_available_rest_versions() + if SAN_REQUIRED_API_VERSION in api_version: + apps = array.list_apps() + for app in range(0, len(apps)): + appname = apps[app]['name'] + apps_facts[appname] = { + 'version': apps[app]['version'], + 'status': apps[app]['status'], + 'description': apps[app]['description'], + } + return apps_facts + + def generate_vgroups_dict(array): vgroups_facts = {} api_version = array._list_available_rest_versions() @@ -572,7 +620,7 @@ def generate_vgroups_dict(array): return vgroups_facts -def generate_offload_dict(array): +def generate_nfs_offload_dict(array): offload_facts = {} api_version = array._list_available_rest_versions() if AC_REQUIRED_API_VERSION in api_version: @@ -589,6 +637,22 @@ def generate_offload_dict(array): return offload_facts +def generate_s3_offload_dict(array): + offload_facts = {} + api_version = array._list_available_rest_versions() + if S3_REQUIRED_API_VERSION in api_version: + offload = array.list_s3_offload() + for target in range(0, len(offload)): + offloadt = offload[target]['name'] + offload_facts[offloadt] = { + 'status': offload[target]['status'], + 'bucket': offload[target]['bucket'], + 'protocol': offload[target]['protocol'], + 'access_key_id': offload[target]['access_key_id'], + } + return offload_facts + + def generate_hgroups_dict(array): hgroups_facts = {} hgroups = array.list_hgroups() @@ -636,7 +700,8 @@ def main(): subset = [test.lower() for test in module.params['gather_subset']] valid_subsets = ('all', 'minimum', 'config', 'performance', 'capacity', 'network', 'subnet', 'interfaces', 'hgroups', 'pgroups', - 'hosts', 'volumes', 'snapshots', 'pods', 'vgroups', 'offload') + 'hosts', 'volumes', 'snapshots', 'pods', 'vgroups', + 'offload', 'apps') subset_test = (test in valid_subsets for test in subset) if not all(subset_test): module.fail_json(msg="value must gather_subset must be one or more of: %s, got: %s" @@ -673,7 +738,10 @@ def main(): if 'vgroups' in subset or 'all' in subset: facts['vgroups'] = generate_vgroups_dict(array) if 'offload' in subset or 'all' in subset: - facts['offload'] = generate_offload_dict(array) + facts['nfs_offload'] = generate_nfs_offload_dict(array) + facts['s3_offload'] = generate_s3_offload_dict(array) + if 'apps' in subset or 'all' in subset: + facts['apps'] = generate_apps_dict(array) module.exit_json(ansible_facts={'ansible_purefa_facts': facts})