diff --git a/__init__.py b/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/__init__.py
diff --git a/baas-1601-dc1/ec2.ini b/baas-1601-dc1/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/baas-1601-dc1/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/baas-1601-dc1/ec2.py b/baas-1601-dc1/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/baas-1601-dc1/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/baas-1601-dc1/inventory b/baas-1601-dc1/inventory
deleted file mode 100644
index 71009f3..0000000
--- a/baas-1601-dc1/inventory
+++ /dev/null
@@ -1,68 +0,0 @@
-[tag_Name_dc1_n0]
-[tag_Name_dc1_n1]
-[tag_Name_dc1_n2]
-[tag_Name_dc1_n3]
-[tag_Name_dc1_n4]
-[tag_Name_dc1_n5]
-[tag_Name_dc1_n6]
-[tag_Name_dc1_n7]
-[tag_Name_dc1_n8]
-[tag_Name_dc1_n9]
-[tag_Name_dc1_n10]
-
-[control:children]
-tag_Name_dc1_n0
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-tag_Name_dc1_n6
-tag_Name_dc1_n7
-tag_Name_dc1_n8
-tag_Name_dc1_n9
-tag_Name_dc1_n10
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-tag_Name_dc1_n6
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc1_n7
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-dc-1-cassandra
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc1_n8
-tag_Name_dc1_n9
-tag_Name_dc1_n10
-
-[dc-1-ms:children]
-tag_Name_dc1_n1
diff --git a/baas-1701-dc5-dc6/ec2.ini b/baas-1701-dc5-dc6/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/baas-1701-dc5-dc6/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/baas-1701-dc5-dc6/ec2.py b/baas-1701-dc5-dc6/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/baas-1701-dc5-dc6/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/baas-1701-dc5-dc6/inventory-dc5 b/baas-1701-dc5-dc6/inventory-dc5
deleted file mode 100644
index dc769fe..0000000
--- a/baas-1701-dc5-dc6/inventory-dc5
+++ /dev/null
@@ -1,67 +0,0 @@
-[tag_Name_dc5_n1]
-[tag_Name_dc5_n2]
-[tag_Name_dc5_n3]
-[tag_Name_dc5_n4]
-[tag_Name_dc5_n5]
-[tag_Name_dc5_n6]
-[tag_Name_dc5_n7]
-[tag_Name_dc5_n8]
-[tag_Name_dc5_n9]
-[tag_Name_dc5_n10]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc5_n7
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-dc-1-cassandra
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc5_n7
diff --git a/baas-1701-dc5-dc6/inventory-dc6 b/baas-1701-dc5-dc6/inventory-dc6
deleted file mode 100644
index 509f36c..0000000
--- a/baas-1701-dc5-dc6/inventory-dc6
+++ /dev/null
@@ -1,67 +0,0 @@
-[tag_Name_dc6_n1]
-[tag_Name_dc6_n2]
-[tag_Name_dc6_n3]
-[tag_Name_dc6_n4]
-[tag_Name_dc6_n5]
-[tag_Name_dc6_n6]
-[tag_Name_dc6_n7]
-[tag_Name_dc6_n8]
-[tag_Name_dc6_n9]
-[tag_Name_dc6_n10]
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[elastic:children]
-dc-2-elastic
-
-[dc-2-elastic:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-
-[baas:children]
-dc-2-baas
-
-[dc-2-baas:children]
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-
-[portal:children]
-dc-2-portal
-
-[dc-2-portal:children]
-tag_Name_dc6_n7
-
-[ds:children]
-dc-2-ds
-
-[dc-2-ds:children]
-dc-2-cassandra
-
-[cassandra:children]
-dc-2-cassandra
-
-[dc-2-cassandra:children]
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc6_n7
diff --git a/baas-1701-dc5/ec2.ini b/baas-1701-dc5/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/baas-1701-dc5/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/baas-1701-dc5/ec2.py b/baas-1701-dc5/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/baas-1701-dc5/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/baas-1701-dc5/inventory b/baas-1701-dc5/inventory
deleted file mode 100644
index dc769fe..0000000
--- a/baas-1701-dc5/inventory
+++ /dev/null
@@ -1,67 +0,0 @@
-[tag_Name_dc5_n1]
-[tag_Name_dc5_n2]
-[tag_Name_dc5_n3]
-[tag_Name_dc5_n4]
-[tag_Name_dc5_n5]
-[tag_Name_dc5_n6]
-[tag_Name_dc5_n7]
-[tag_Name_dc5_n8]
-[tag_Name_dc5_n9]
-[tag_Name_dc5_n10]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc5_n7
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-dc-1-cassandra
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc5_n7
diff --git a/baas-1701-dc6/ec2.ini b/baas-1701-dc6/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/baas-1701-dc6/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/baas-1701-dc6/ec2.py b/baas-1701-dc6/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/baas-1701-dc6/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/baas-1701-dc6/inventory b/baas-1701-dc6/inventory
deleted file mode 100644
index 454f2d4..0000000
--- a/baas-1701-dc6/inventory
+++ /dev/null
@@ -1,67 +0,0 @@
-[tag_Name_dc6_n1]
-[tag_Name_dc6_n2]
-[tag_Name_dc6_n3]
-[tag_Name_dc6_n4]
-[tag_Name_dc6_n5]
-[tag_Name_dc6_n6]
-[tag_Name_dc6_n7]
-[tag_Name_dc6_n8]
-[tag_Name_dc6_n9]
-[tag_Name_dc6_n10]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc6_n7
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-dc-1-cassandra
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc6_n7
diff --git a/baas-1701-dc7/ec2.ini b/baas-1701-dc7/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/baas-1701-dc7/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/baas-1701-dc7/ec2.py b/baas-1701-dc7/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/baas-1701-dc7/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/baas-1701-dc7/inventory b/baas-1701-dc7/inventory
deleted file mode 100644
index a87db34..0000000
--- a/baas-1701-dc7/inventory
+++ /dev/null
@@ -1,67 +0,0 @@
-[tag_Name_dc7_n11]
-[tag_Name_dc7_n12]
-[tag_Name_dc7_n13]
-[tag_Name_dc7_n14]
-[tag_Name_dc7_n15]
-[tag_Name_dc7_n16]
-[tag_Name_dc7_n17]
-[tag_Name_dc7_n18]
-[tag_Name_dc7_n19]
-[tag_Name_dc7_n20]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n11
-tag_Name_dc7_n12
-tag_Name_dc7_n13
-tag_Name_dc7_n14
-tag_Name_dc7_n15
-tag_Name_dc7_n16
-tag_Name_dc7_n17
-tag_Name_dc7_n18
-tag_Name_dc7_n19
-tag_Name_dc7_n20
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc7_n11
-tag_Name_dc7_n12
-tag_Name_dc7_n13
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc7_n14
-tag_Name_dc7_n15
-tag_Name_dc7_n16
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc7_n17
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-dc-1-cassandra
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc7_n18
-tag_Name_dc7_n19
-tag_Name_dc7_n20
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc7_n17
diff --git a/edge-1601-aio/ec2.ini b/edge-1601-aio/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-aio/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-aio/ec2.py b/edge-1601-aio/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-aio/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-cassandra-replication-factor-lab/inventory-dc1 b/edge-1601-cassandra-replication-factor-lab/inventory-dc1
deleted file mode 100644
index 1d95871..0000000
--- a/edge-1601-cassandra-replication-factor-lab/inventory-dc1
+++ /dev/null
@@ -1,160 +0,0 @@
-[tag_Name_dc1_n1]
-54.172.3.199
-
-[tag_Name_dc1_n2]
-52.206.192.26
-
-[tag_Name_dc1_n3]
-54.227.166.177
-
-[tag_Name_dc1_n4]
-54.89.173.227
-
-[tag_Name_dc1_n5]
-54.88.227.64
-
-[tag_Name_dc1_n6]
-54.165.100.53
-
-[tag_Name_dc1_n7]
-54.172.208.7
-
-[tag_Name_dc1_n8]
-54.172.166.239
-
-[tag_Name_dc1_n9]
-54.209.169.95
-
-[tag_Name_dc1_n10]
-52.90.24.114
-
-[tag_Name_dc1_n11]
-52.91.219.87
-
-[tag_Name_dc1_n12]
-54.144.242.20
-
-[tag_Name_dc1_n13]
-54.197.27.231
-
-[tag_Name_dc1_n14]
-54.225.54.117
-
-[tag_Name_dc1_n15]
-54.146.29.98
-
-[tag_Name_dc1_n16]
-54.227.180.97
-
-[tag_Name_dc1_n17]
-54.174.221.137
-
-[tag_Name_dc1_n18]
-54.227.183.30
-
-[tag_Name_dc1_n19]
-54.235.54.24
-
-[tag_Name_dc1_n20]
-54.86.64.45
-
-[tag_Name_dc1_n21]
-52.23.172.34
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-tag_Name_dc1_n6
-tag_Name_dc1_n7
-tag_Name_dc1_n8
-tag_Name_dc1_n9
-tag_Name_dc1_n10
-tag_Name_dc1_n11
-tag_Name_dc1_n12
-tag_Name_dc1_n13
-tag_Name_dc1_n14
-tag_Name_dc1_n15
-tag_Name_dc1_n16
-tag_Name_dc1_n17
-tag_Name_dc1_n18
-tag_Name_dc1_n19
-tag_Name_dc1_n20
-tag_Name_dc1_n21
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-tag_Name_dc1_n6
-tag_Name_dc1_n7
-tag_Name_dc1_n8
-tag_Name_dc1_n9
-tag_Name_dc1_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc1_n11
-tag_Name_dc1_n12
-tag_Name_dc1_n13
-tag_Name_dc1_n14
-tag_Name_dc1_n15
-tag_Name_dc1_n16
-tag_Name_dc1_n17
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc1_n18
-tag_Name_dc1_n19
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc1_n20
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc1_n21
diff --git a/edge-1601-cassandra-replication-factor-lab/inventory-dc2 b/edge-1601-cassandra-replication-factor-lab/inventory-dc2
deleted file mode 100644
index b8f96fd..0000000
--- a/edge-1601-cassandra-replication-factor-lab/inventory-dc2
+++ /dev/null
@@ -1,161 +0,0 @@
-
-[tag_Name_dc2_n1]
-54.164.60.87
-
-[tag_Name_dc2_n2]
-54.89.192.72
-
-[tag_Name_dc2_n3]
-107.21.21.110
-
-[tag_Name_dc2_n4]
-52.207.226.72
-
-[tag_Name_dc2_n5]
-54.87.145.51
-
-[tag_Name_dc2_n6]
-54.165.167.56
-
-[tag_Name_dc2_n7]
-54.198.137.84
-
-[tag_Name_dc2_n8]
-54.224.112.82
-
-[tag_Name_dc2_n9]
-54.85.58.122
-
-[tag_Name_dc2_n10]
-107.22.137.210
-
-[tag_Name_dc2_n11]
-54.198.195.14
-
-[tag_Name_dc2_n12]
-52.201.252.231
-
-[tag_Name_dc2_n13]
-54.86.147.123
-
-[tag_Name_dc2_n14]
-54.173.159.240
-
-[tag_Name_dc2_n15]
-54.164.126.156
-
-[tag_Name_dc2_n16]
-54.175.40.154
-
-[tag_Name_dc2_n17]
-54.82.169.123
-
-[tag_Name_dc2_n18]
-52.201.248.63
-
-[tag_Name_dc2_n19]
-54.157.238.96
-
-[tag_Name_dc2_n20]
-54.164.102.91
-
-[tag_Name_dc2_n21]
-54.172.205.234
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-tag_Name_dc2_n6
-tag_Name_dc2_n7
-tag_Name_dc2_n8
-tag_Name_dc2_n9
-tag_Name_dc2_n10
-tag_Name_dc2_n11
-tag_Name_dc2_n12
-tag_Name_dc2_n13
-tag_Name_dc2_n14
-tag_Name_dc2_n15
-tag_Name_dc2_n16
-tag_Name_dc2_n17
-tag_Name_dc2_n18
-tag_Name_dc2_n19
-tag_Name_dc2_n20
-tag_Name_dc2_n21
-
-[ds:children]
-dc-2-ds
-
-[dc-2-ds:children]
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-tag_Name_dc2_n6
-tag_Name_dc2_n7
-tag_Name_dc2_n8
-tag_Name_dc2_n9
-tag_Name_dc2_n10
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-
-[ui:children]
-dc-2-ui
-
-[dc-2-ui:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-
-[ldap:children]
-dc-2-ldap
-
-[dc-2-ldap:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-
-[rmp:children]
-dc-2-rmp
-
-[dc-2-rmp:children]
-tag_Name_dc2_n11
-tag_Name_dc2_n12
-tag_Name_dc2_n13
-tag_Name_dc2_n14
-tag_Name_dc2_n15
-tag_Name_dc2_n16
-tag_Name_dc2_n17
-
-[qpid:children]
-dc-2-qpid
-
-[dc-2-qpid:children]
-tag_Name_dc2_n18
-tag_Name_dc2_n19
-
-[pg:children]
-dc-2-pg
-
-[dc-2-pg:children]
-dc-2-pgmaster
-dc-2-pgstandby
-
-[pgmaster:children]
-dc-2-pgmaster
-
-[dc-2-pgmaster:children]
-tag_Name_dc2_n20
-
-[pgstandby:children]
-dc-2-pgstandby
-
-[dc-2-pgstandby:children]
-tag_Name_dc2_n21
diff --git a/edge-1601-dc1-dc2/ec2.ini b/edge-1601-dc1-dc2/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc1-dc2/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc1-dc2/ec2.py b/edge-1601-dc1-dc2/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc1-dc2/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc1-dc2/inventory-dc1 b/edge-1601-dc1-dc2/inventory-dc1
deleted file mode 100644
index a26a6fe..0000000
--- a/edge-1601-dc1-dc2/inventory-dc1
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc1_n1]
-[tag_Name_dc1_n2]
-[tag_Name_dc1_n3]
-[tag_Name_dc1_n4]
-[tag_Name_dc1_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc1_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc1_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc1_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc1_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc1_n5
diff --git a/edge-1601-dc1-dc2/inventory-dc2 b/edge-1601-dc1-dc2/inventory-dc2
deleted file mode 100644
index 71a7ba8..0000000
--- a/edge-1601-dc1-dc2/inventory-dc2
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc2_n1]
-[tag_Name_dc2_n2]
-[tag_Name_dc2_n3]
-[tag_Name_dc2_n4]
-[tag_Name_dc2_n5]
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[ds:children]
-dc-2-ds
-
-[dc-2-ds:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc2_n1
-
-[ui:children]
-dc-2-ui
-
-[dc-2-ui:children]
-tag_Name_dc2_n1
-
-[ldap:children]
-dc-2-ldap
-
-[dc-2-ldap:children]
-tag_Name_dc2_n1
-
-[rmp:children]
-dc-2-rmp
-
-[dc-2-rmp:children]
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[qpid:children]
-dc-2-qpid
-
-[dc-2-qpid:children]
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[pg:children]
-dc-2-pg
-
-[dc-2-pg:children]
-dc-2-pgmaster
-dc-2-pgstandby
-
-[pgmaster:children]
-dc-2-pgmaster
-
-[dc-2-pgmaster:children]
-tag_Name_dc2_n4
-
-[pgstandby:children]
-dc-2-pgstandby
-
-[dc-2-pgstandby:children]
-tag_Name_dc2_n5
diff --git a/edge-1601-dc1-dc2/inventory-haproxy b/edge-1601-dc1-dc2/inventory-haproxy
deleted file mode 100644
index 6b45b6a..0000000
--- a/edge-1601-dc1-dc2/inventory-haproxy
+++ /dev/null
@@ -1,7 +0,0 @@
-[tag_Name_dc10_n1]
-
-[planet:children]
-haproxy
-
-[haproxy:children]
-tag_Name_dc0_n1
diff --git a/edge-1601-dc1/ec2.ini b/edge-1601-dc1/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc1/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc1/ec2.py b/edge-1601-dc1/ec2.py
deleted file mode 100755
index 25b3ab4..0000000
--- a/edge-1601-dc1/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-            config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc1/inventory b/edge-1601-dc1/inventory
deleted file mode 100644
index a26a6fe..0000000
--- a/edge-1601-dc1/inventory
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc1_n1]
-[tag_Name_dc1_n2]
-[tag_Name_dc1_n3]
-[tag_Name_dc1_n4]
-[tag_Name_dc1_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc1_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc1_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc1_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc1_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc1_n5
diff --git a/edge-1601-dc2-dc3/ec2.ini b/edge-1601-dc2-dc3/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc2-dc3/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc2-dc3/ec2.py b/edge-1601-dc2-dc3/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc2-dc3/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc2/inventory b/edge-1601-dc2/inventory
deleted file mode 100644
index 3bb90ab..0000000
--- a/edge-1601-dc2/inventory
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc2_n1]
-[tag_Name_dc2_n2]
-[tag_Name_dc2_n3]
-[tag_Name_dc2_n4]
-[tag_Name_dc2_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc2_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc2_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc2_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc2_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc2_n5
diff --git a/edge-1601-dc3-dc4/ec2.ini b/edge-1601-dc3-dc4/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc3-dc4/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc3-dc4/ec2.py b/edge-1601-dc3-dc4/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc3-dc4/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc3-dc4/inventory-dc3 b/edge-1601-dc3-dc4/inventory-dc3
deleted file mode 100644
index 0b97282..0000000
--- a/edge-1601-dc3-dc4/inventory-dc3
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n5
diff --git a/edge-1601-dc3-dc4/inventory-dc4 b/edge-1601-dc3-dc4/inventory-dc4
deleted file mode 100644
index 93b42da..0000000
--- a/edge-1601-dc3-dc4/inventory-dc4
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc4_n1]
-[tag_Name_dc4_n2]
-[tag_Name_dc4_n3]
-[tag_Name_dc4_n4]
-[tag_Name_dc4_n5]
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc4_n1
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-tag_Name_dc4_n5
-
-[ds:children]
-dc-2-ds
-
-[dc-2-ds:children]
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc4_n1
-
-[ui:children]
-dc-2-ui
-
-[dc-2-ui:children]
-tag_Name_dc4_n1
-
-[ldap:children]
-dc-2-ldap
-
-[dc-2-ldap:children]
-tag_Name_dc4_n1
-
-[rmp:children]
-dc-2-rmp
-
-[dc-2-rmp:children]
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-
-[qpid:children]
-dc-2-qpid
-
-[dc-2-qpid:children]
-tag_Name_dc4_n4
-tag_Name_dc4_n5
-
-[pg:children]
-dc-2-pg
-
-[dc-2-pg:children]
-dc-2-pgmaster
-dc-2-pgstandby
-
-[pgmaster:children]
-dc-2-pgmaster
-
-[dc-2-pgmaster:children]
-tag_Name_dc4_n4
-
-[pgstandby:children]
-dc-2-pgstandby
-
-[dc-2-pgstandby:children]
-tag_Name_dc4_n5
diff --git a/edge-1601-dc3/ec2.ini b/edge-1601-dc3/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc3/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc3/ec2.py b/edge-1601-dc3/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc3/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc3/inventory b/edge-1601-dc3/inventory
deleted file mode 100644
index 0b97282..0000000
--- a/edge-1601-dc3/inventory
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n5
diff --git a/edge-1601-dc4/ec2.ini b/edge-1601-dc4/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc4/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc4/ec2.py b/edge-1601-dc4/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc4/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc4/inventory b/edge-1601-dc4/inventory
deleted file mode 100644
index 0b97282..0000000
--- a/edge-1601-dc4/inventory
+++ /dev/null
@@ -1,74 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n5
diff --git a/edge-1601-dc5-dc6/ec2.ini b/edge-1601-dc5-dc6/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc5-dc6/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc5-dc6/ec2.py b/edge-1601-dc5-dc6/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc5-dc6/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc5-dc6/inventory-dc5 b/edge-1601-dc5-dc6/inventory-dc5
deleted file mode 100644
index f706500..0000000
--- a/edge-1601-dc5-dc6/inventory-dc5
+++ /dev/null
@@ -1,137 +0,0 @@
-[tag_Name_dc5_n1]
-[tag_Name_dc5_n2]
-[tag_Name_dc5_n3]
-[tag_Name_dc5_n4]
-[tag_Name_dc5_n5]
-[tag_Name_dc5_n6]
-[tag_Name_dc5_n7]
-[tag_Name_dc5_n8]
-[tag_Name_dc5_n9]
-[tag_Name_dc5_n10]
-[tag_Name_dc5_n11]
-[tag_Name_dc5_n12]
-[tag_Name_dc5_n13]
-[tag_Name_dc5_n14]
-[tag_Name_dc5_n15]
-[tag_Name_dc5_n16]
-[tag_Name_dc5_n17]
-[tag_Name_dc5_n18]
-[tag_Name_dc5_n19]
-[tag_Name_dc5_n20]
-[tag_Name_dc5_n21]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-tag_Name_dc5_n11
-tag_Name_dc5_n12
-tag_Name_dc5_n13
-tag_Name_dc5_n14
-tag_Name_dc5_n15
-tag_Name_dc5_n16
-tag_Name_dc5_n17
-tag_Name_dc5_n18
-tag_Name_dc5_n19
-tag_Name_dc5_n20
-tag_Name_dc5_n21
-
-[tag_Name_dc5_n5:vars]
-zk_observer=true
-
-[tag_Name_dc5_n6:vars]
-zk_observer=true
-
-[tag_Name_dc5_n7:vars]
-zk_observer=true
-
-[tag_Name_dc5_n8:vars]
-zk_observer=true
-
-[tag_Name_dc5_n9:vars]
-zk_observer=true
-
-[tag_Name_dc5_n10:vars]
-zk_observer=true
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc5_n11
-tag_Name_dc5_n12
-tag_Name_dc5_n13
-tag_Name_dc5_n14
-tag_Name_dc5_n15
-tag_Name_dc5_n16
-tag_Name_dc5_n17
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc5_n18
-tag_Name_dc5_n19
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc5_n20
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc5_n21
diff --git a/edge-1601-dc5-dc6/inventory-dc6 b/edge-1601-dc5-dc6/inventory-dc6
deleted file mode 100644
index 0dbf6b1..0000000
--- a/edge-1601-dc5-dc6/inventory-dc6
+++ /dev/null
@@ -1,140 +0,0 @@
-[tag_Name_dc6_n1]
-[tag_Name_dc6_n2]
-[tag_Name_dc6_n3]
-[tag_Name_dc6_n4]
-[tag_Name_dc6_n5]
-[tag_Name_dc6_n6]
-[tag_Name_dc6_n7]
-[tag_Name_dc6_n8]
-[tag_Name_dc6_n9]
-[tag_Name_dc6_n10]
-[tag_Name_dc6_n11]
-[tag_Name_dc6_n12]
-[tag_Name_dc6_n13]
-[tag_Name_dc6_n14]
-[tag_Name_dc6_n15]
-[tag_Name_dc6_n16]
-[tag_Name_dc6_n17]
-[tag_Name_dc6_n18]
-[tag_Name_dc6_n19]
-[tag_Name_dc6_n20]
-[tag_Name_dc6_n21]
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-tag_Name_dc6_n11
-tag_Name_dc6_n12
-tag_Name_dc6_n13
-tag_Name_dc6_n14
-tag_Name_dc6_n15
-tag_Name_dc6_n16
-tag_Name_dc6_n17
-tag_Name_dc6_n18
-tag_Name_dc6_n19
-tag_Name_dc6_n20
-tag_Name_dc6_n21
-
-[ds:children]
-dc-2-ds
-
-[tag_Name_dc6_n4:vars]
-zk_observer=true
-
-[tag_Name_dc6_n5:vars]
-zk_observer=true
-
-[tag_Name_dc6_n6:vars]
-zk_observer=true
-
-[tag_Name_dc6_n7:vars]
-zk_observer=true
-
-[tag_Name_dc6_n8:vars]
-zk_observer=true
-
-[tag_Name_dc6_n9:vars]
-zk_observer=true
-
-[tag_Name_dc6_n10:vars]
-zk_observer=true
-
-[dc-2-ds:children]
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[ui:children]
-dc-2-ui
-
-[dc-2-ui:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[ldap:children]
-dc-2-ldap
-
-[dc-2-ldap:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[rmp:children]
-dc-2-rmp
-
-[dc-2-rmp:children]
-tag_Name_dc6_n11
-tag_Name_dc6_n12
-tag_Name_dc6_n13
-tag_Name_dc6_n14
-tag_Name_dc6_n15
-tag_Name_dc6_n16
-tag_Name_dc6_n17
-
-[qpid:children]
-dc-2-qpid
-
-[dc-2-qpid:children]
-tag_Name_dc6_n18
-tag_Name_dc6_n19
-
-[pg:children]
-dc-2-pg
-
-[dc-2-pg:children]
-dc-2-pgmaster
-dc-2-pgstandby
-
-[pgmaster:children]
-dc-2-pgmaster
-
-[dc-2-pgmaster:children]
-tag_Name_dc6_n20
-
-[pgstandby:children]
-dc-2-pgstandby
-
-[dc-2-pgstandby:children]
-tag_Name_dc6_n21
diff --git a/edge-1601-dc5-dc6/inventory-haproxy b/edge-1601-dc5-dc6/inventory-haproxy
deleted file mode 100644
index 19c82a2..0000000
--- a/edge-1601-dc5-dc6/inventory-haproxy
+++ /dev/null
@@ -1,4 +0,0 @@
-[tag_Name_dc10_n1]
-
-[haproxy:children]
-tag_Name_dc10_n1
diff --git a/edge-1601-dc5/ec2.ini b/edge-1601-dc5/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc5/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc5/ec2.py b/edge-1601-dc5/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc5/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc5/inventory b/edge-1601-dc5/inventory
deleted file mode 100644
index 4654714..0000000
--- a/edge-1601-dc5/inventory
+++ /dev/null
@@ -1,119 +0,0 @@
-[tag_Name_dc5_n1]
-[tag_Name_dc5_n2]
-[tag_Name_dc5_n3]
-[tag_Name_dc5_n4]
-[tag_Name_dc5_n5]
-[tag_Name_dc5_n6]
-[tag_Name_dc5_n7]
-[tag_Name_dc5_n8]
-[tag_Name_dc5_n9]
-[tag_Name_dc5_n10]
-[tag_Name_dc5_n11]
-[tag_Name_dc5_n12]
-[tag_Name_dc5_n13]
-[tag_Name_dc5_n14]
-[tag_Name_dc5_n15]
-[tag_Name_dc5_n16]
-[tag_Name_dc5_n17]
-[tag_Name_dc5_n18]
-[tag_Name_dc5_n19]
-[tag_Name_dc5_n20]
-[tag_Name_dc5_n21]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-tag_Name_dc5_n11
-tag_Name_dc5_n12
-tag_Name_dc5_n13
-tag_Name_dc5_n14
-tag_Name_dc5_n15
-tag_Name_dc5_n16
-tag_Name_dc5_n17
-tag_Name_dc5_n18
-tag_Name_dc5_n19
-tag_Name_dc5_n20
-tag_Name_dc5_n21
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-tag_Name_dc5_n6
-tag_Name_dc5_n7
-tag_Name_dc5_n8
-tag_Name_dc5_n9
-tag_Name_dc5_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc5_n11
-tag_Name_dc5_n12
-tag_Name_dc5_n13
-tag_Name_dc5_n14
-tag_Name_dc5_n15
-tag_Name_dc5_n16
-tag_Name_dc5_n17
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc5_n18
-tag_Name_dc5_n19
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc5_n20
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc5_n21
diff --git a/edge-1601-dc6/ec2.ini b/edge-1601-dc6/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1601-dc6/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1601-dc6/ec2.py b/edge-1601-dc6/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1601-dc6/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-dc6/inventory b/edge-1601-dc6/inventory
deleted file mode 100644
index 08fc86f..0000000
--- a/edge-1601-dc6/inventory
+++ /dev/null
@@ -1,119 +0,0 @@
-[tag_Name_dc6_n1]
-[tag_Name_dc6_n2]
-[tag_Name_dc6_n3]
-[tag_Name_dc6_n4]
-[tag_Name_dc6_n5]
-[tag_Name_dc6_n6]
-[tag_Name_dc6_n7]
-[tag_Name_dc6_n8]
-[tag_Name_dc6_n9]
-[tag_Name_dc6_n10]
-[tag_Name_dc6_n11]
-[tag_Name_dc6_n12]
-[tag_Name_dc6_n13]
-[tag_Name_dc6_n14]
-[tag_Name_dc6_n15]
-[tag_Name_dc6_n16]
-[tag_Name_dc6_n17]
-[tag_Name_dc6_n18]
-[tag_Name_dc6_n19]
-[tag_Name_dc6_n20]
-[tag_Name_dc6_n21]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-tag_Name_dc6_n11
-tag_Name_dc6_n12
-tag_Name_dc6_n13
-tag_Name_dc6_n14
-tag_Name_dc6_n15
-tag_Name_dc6_n16
-tag_Name_dc6_n17
-tag_Name_dc6_n18
-tag_Name_dc6_n19
-tag_Name_dc6_n20
-tag_Name_dc6_n21
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc6_n3
-tag_Name_dc6_n4
-tag_Name_dc6_n5
-tag_Name_dc6_n6
-tag_Name_dc6_n7
-tag_Name_dc6_n8
-tag_Name_dc6_n9
-tag_Name_dc6_n10
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc6_n1
-tag_Name_dc6_n2
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc6_n11
-tag_Name_dc6_n12
-tag_Name_dc6_n13
-tag_Name_dc6_n14
-tag_Name_dc6_n15
-tag_Name_dc6_n16
-tag_Name_dc6_n17
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc6_n18
-tag_Name_dc6_n19
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc6_n20
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc6_n21
diff --git a/edge-1605-dc3/ec2.ini b/edge-1605-dc3/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1605-dc3/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1605-dc3/ec2.py b/edge-1605-dc3/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1605-dc3/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1605-dc3/inventory b/edge-1605-dc3/inventory
deleted file mode 100644
index 63fe321..0000000
--- a/edge-1605-dc3/inventory
+++ /dev/null
@@ -1,78 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-[tag_Name_dc3_n6]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n5
-
-[mirror:children]
-tag_Name_dc3_n6
\ No newline at end of file
diff --git a/edge-1609-dc2/ec2.ini b/edge-1609-dc2/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1609-dc2/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1609-dc2/ec2.py b/edge-1609-dc2/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1609-dc2/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1609-dc2/inventory b/edge-1609-dc2/inventory
deleted file mode 100644
index 436da8b..0000000
--- a/edge-1609-dc2/inventory
+++ /dev/null
@@ -1,75 +0,0 @@
-[tag_Name_dc2_n1]
-[tag_Name_dc2_n2]
-[tag_Name_dc2_n3]
-[tag_Name_dc2_n4]
-[tag_Name_dc2_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc2_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc2_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc2_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc2_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc2_n5
-
diff --git a/edge-1609-dc3-dc4/ec2.ini b/edge-1609-dc3-dc4/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1609-dc3-dc4/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1609-dc3-dc4/ec2.py b/edge-1609-dc3-dc4/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1609-dc3-dc4/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1609-dc3-dc4/inventory-dc3 b/edge-1609-dc3-dc4/inventory-dc3
deleted file mode 100644
index 27e2114..0000000
--- a/edge-1609-dc3-dc4/inventory-dc3
+++ /dev/null
@@ -1,87 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-[tag_Name_dc3_n6]
-[tag_Name_dc3_n7]
-[tag_Name_dc3_n8]
-[tag_Name_dc3_n9]
-[tag_Name_dc3_n10]
-[tag_Name_dc3_n11]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-tag_Name_dc3_n6
-tag_Name_dc3_n7
-tag_Name_dc3_n8
-tag_Name_dc3_n9
-tag_Name_dc3_n10
-tag_Name_dc3_n11
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n5
-tag_Name_dc3_n6
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n7
-tag_Name_dc3_n8
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n10
-
diff --git a/edge-1609-dc3-dc4/inventory-dc4 b/edge-1609-dc3-dc4/inventory-dc4
deleted file mode 100644
index 1fa13b5..0000000
--- a/edge-1609-dc3-dc4/inventory-dc4
+++ /dev/null
@@ -1,87 +0,0 @@
-[tag_Name_dc4_n1]
-[tag_Name_dc4_n2]
-[tag_Name_dc4_n3]
-[tag_Name_dc4_n4]
-[tag_Name_dc4_n5]
-[tag_Name_dc4_n6]
-[tag_Name_dc4_n7]
-[tag_Name_dc4_n8]
-[tag_Name_dc4_n9]
-[tag_Name_dc4_n10]
-[tag_Name_dc4_n11]
-
-[planet:children]
-dc-2
-
-[dc-2:children]
-tag_Name_dc4_n1
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-tag_Name_dc4_n5
-tag_Name_dc4_n6
-tag_Name_dc4_n7
-tag_Name_dc4_n8
-tag_Name_dc4_n9
-tag_Name_dc4_n10
-tag_Name_dc4_n11
-
-[ds:children]
-dc-2-ds
-
-[dc-2-ds:children]
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-
-[ms:children]
-dc-2-ms
-
-[dc-2-ms:children]
-tag_Name_dc4_n1
-
-[ui:children]
-dc-2-ui
-
-[dc-2-ui:children]
-tag_Name_dc4_n1
-
-[ldap:children]
-dc-2-ldap
-
-[dc-2-ldap:children]
-tag_Name_dc4_n1
-
-[rmp:children]
-dc-2-rmp
-
-[dc-2-rmp:children]
-tag_Name_dc4_n5
-tag_Name_dc4_n6
-
-[qpid:children]
-dc-2-qpid
-
-[dc-2-qpid:children]
-tag_Name_dc4_n7
-tag_Name_dc4_n8
-
-[pg:children]
-dc-2-pg
-
-[dc-2-pg:children]
-dc-2-pgmaster
-dc-2-pgstandby
-
-[pgmaster:children]
-dc-2-pgmaster
-
-[dc-2-pgmaster:children]
-tag_Name_dc4_n9
-
-[pgstandby:children]
-dc-2-pgstandby
-
-[dc-2-pgstandby:children]
-tag_Name_dc4_n10
-
diff --git a/edge-1609-dc3/ec2.ini b/edge-1609-dc3/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1609-dc3/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1609-dc3/ec2.py b/edge-1609-dc3/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1609-dc3/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1609-dc3/inventory b/edge-1609-dc3/inventory
deleted file mode 100644
index 27e2114..0000000
--- a/edge-1609-dc3/inventory
+++ /dev/null
@@ -1,87 +0,0 @@
-[tag_Name_dc3_n1]
-[tag_Name_dc3_n2]
-[tag_Name_dc3_n3]
-[tag_Name_dc3_n4]
-[tag_Name_dc3_n5]
-[tag_Name_dc3_n6]
-[tag_Name_dc3_n7]
-[tag_Name_dc3_n8]
-[tag_Name_dc3_n9]
-[tag_Name_dc3_n10]
-[tag_Name_dc3_n11]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc3_n1
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-tag_Name_dc3_n5
-tag_Name_dc3_n6
-tag_Name_dc3_n7
-tag_Name_dc3_n8
-tag_Name_dc3_n9
-tag_Name_dc3_n10
-tag_Name_dc3_n11
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc3_n2
-tag_Name_dc3_n3
-tag_Name_dc3_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc3_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc3_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc3_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc3_n5
-tag_Name_dc3_n6
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc3_n7
-tag_Name_dc3_n8
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc3_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc3_n10
-
diff --git a/edge-1609-dc4/ec2.ini b/edge-1609-dc4/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1609-dc4/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1609-dc4/ec2.py b/edge-1609-dc4/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1609-dc4/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1609-dc4/inventory b/edge-1609-dc4/inventory
deleted file mode 100644
index 47150f9..0000000
--- a/edge-1609-dc4/inventory
+++ /dev/null
@@ -1,87 +0,0 @@
-[tag_Name_dc4_n1]
-[tag_Name_dc4_n2]
-[tag_Name_dc4_n3]
-[tag_Name_dc4_n4]
-[tag_Name_dc4_n5]
-[tag_Name_dc4_n6]
-[tag_Name_dc4_n7]
-[tag_Name_dc4_n8]
-[tag_Name_dc4_n9]
-[tag_Name_dc4_n10]
-[tag_Name_dc4_n11]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc4_n1
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-tag_Name_dc4_n5
-tag_Name_dc4_n6
-tag_Name_dc4_n7
-tag_Name_dc4_n8
-tag_Name_dc4_n9
-tag_Name_dc4_n10
-tag_Name_dc4_n11
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc4_n2
-tag_Name_dc4_n3
-tag_Name_dc4_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc4_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc4_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc4_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc4_n5
-tag_Name_dc4_n6
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc4_n7
-tag_Name_dc4_n8
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc4_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc4_n10
-
diff --git a/edge-1701-dc1/ec2.ini b/edge-1701-dc1/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1701-dc1/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1701-dc1/ec2.py b/edge-1701-dc1/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1701-dc1/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1701-dc1/inventory b/edge-1701-dc1/inventory
deleted file mode 100644
index 4c90b9e..0000000
--- a/edge-1701-dc1/inventory
+++ /dev/null
@@ -1,75 +0,0 @@
-[tag_Name_dc1_n1]
-[tag_Name_dc1_n2]
-[tag_Name_dc1_n3]
-[tag_Name_dc1_n4]
-[tag_Name_dc1_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc1_n1
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc1_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc1_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc1_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc1_n2
-tag_Name_dc1_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc1_n4
-tag_Name_dc1_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc1_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc1_n5
-
diff --git a/edge-1701-dc2/ec2.ini b/edge-1701-dc2/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1701-dc2/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1701-dc2/ec2.py b/edge-1701-dc2/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1701-dc2/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1701-dc2/inventory b/edge-1701-dc2/inventory
deleted file mode 100644
index 436da8b..0000000
--- a/edge-1701-dc2/inventory
+++ /dev/null
@@ -1,75 +0,0 @@
-[tag_Name_dc2_n1]
-[tag_Name_dc2_n2]
-[tag_Name_dc2_n3]
-[tag_Name_dc2_n4]
-[tag_Name_dc2_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc2_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc2_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc2_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc2_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc2_n5
-
diff --git a/edge-1701-dc5/ec2.ini b/edge-1701-dc5/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1701-dc5/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1701-dc5/ec2.py b/edge-1701-dc5/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1701-dc5/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1701-dc5/inventory b/edge-1701-dc5/inventory
deleted file mode 100644
index 332a944..0000000
--- a/edge-1701-dc5/inventory
+++ /dev/null
@@ -1,75 +0,0 @@
-[tag_Name_dc5_n1]
-[tag_Name_dc5_n2]
-[tag_Name_dc5_n3]
-[tag_Name_dc5_n4]
-[tag_Name_dc5_n5]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc5_n1
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc5_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc5_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc5_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc5_n2
-tag_Name_dc5_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc5_n4
-tag_Name_dc5_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc5_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc5_n5
-
diff --git a/edge-1701-dc7/ec2.ini b/edge-1701-dc7/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-1701-dc7/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-1701-dc7/ec2.py b/edge-1701-dc7/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-1701-dc7/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1701-dc7/inventory b/edge-1701-dc7/inventory
deleted file mode 100644
index 21862f9..0000000
--- a/edge-1701-dc7/inventory
+++ /dev/null
@@ -1,84 +0,0 @@
-[tag_Name_dc7_n1]
-[tag_Name_dc7_n2]
-[tag_Name_dc7_n3]
-[tag_Name_dc7_n4]
-[tag_Name_dc7_n5]
-[tag_Name_dc7_n6]
-[tag_Name_dc7_n7]
-[tag_Name_dc7_n8]
-[tag_Name_dc7_n9]
-[tag_Name_dc7_n10]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n1
-tag_Name_dc7_n2
-tag_Name_dc7_n3
-tag_Name_dc7_n4
-tag_Name_dc7_n5
-tag_Name_dc7_n6
-tag_Name_dc7_n7
-tag_Name_dc7_n8
-tag_Name_dc7_n9
-tag_Name_dc7_n10
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc7_n1
-tag_Name_dc7_n2
-tag_Name_dc7_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc7_n4
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc7_n4
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc7_n4
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc7_n5
-tag_Name_dc7_n6
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc7_n7
-tag_Name_dc7_n8
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc7_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc7_n10
diff --git a/edge-baas-portal-1701-dc7/ec2.ini b/edge-baas-portal-1701-dc7/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edge-baas-portal-1701-dc7/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edge-baas-portal-1701-dc7/ec2.py b/edge-baas-portal-1701-dc7/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edge-baas-portal-1701-dc7/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-baas-portal-1701-dc7/inventory-dc7-baas b/edge-baas-portal-1701-dc7/inventory-dc7-baas
deleted file mode 100644
index d2ae03e..0000000
--- a/edge-baas-portal-1701-dc7/inventory-dc7-baas
+++ /dev/null
@@ -1,55 +0,0 @@
-[tag_Name_dc7_n11]
-[tag_Name_dc7_n12]
-[tag_Name_dc7_n13]
-[tag_Name_dc7_n14]
-[tag_Name_dc7_n15]
-[tag_Name_dc7_n16]
-[tag_Name_dc7_n17]
-[tag_Name_dc7_n18]
-[tag_Name_dc7_n19]
-[tag_Name_dc7_n20]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n11
-tag_Name_dc7_n12
-tag_Name_dc7_n13
-tag_Name_dc7_n14
-tag_Name_dc7_n15
-tag_Name_dc7_n16
-tag_Name_dc7_n17
-tag_Name_dc7_n18
-tag_Name_dc7_n19
-tag_Name_dc7_n20
-
-[elastic:children]
-dc-1-elastic
-
-[dc-1-elastic:children]
-tag_Name_dc7_n11
-tag_Name_dc7_n12
-tag_Name_dc7_n13
-
-[baas:children]
-dc-1-baas
-
-[dc-1-baas:children]
-tag_Name_dc7_n14
-tag_Name_dc7_n15
-tag_Name_dc7_n16
-
-[portal:children]
-dc-1-portal
-
-[dc-1-portal:children]
-tag_Name_dc7_n17
-
-[cassandra:children]
-dc-1-cassandra
-
-[dc-1-cassandra:children]
-tag_Name_dc7_n18
-tag_Name_dc7_n19
-tag_Name_dc7_n20
diff --git a/edge-baas-portal-1701-dc7/inventory-dc7-edge b/edge-baas-portal-1701-dc7/inventory-dc7-edge
deleted file mode 100644
index 21862f9..0000000
--- a/edge-baas-portal-1701-dc7/inventory-dc7-edge
+++ /dev/null
@@ -1,84 +0,0 @@
-[tag_Name_dc7_n1]
-[tag_Name_dc7_n2]
-[tag_Name_dc7_n3]
-[tag_Name_dc7_n4]
-[tag_Name_dc7_n5]
-[tag_Name_dc7_n6]
-[tag_Name_dc7_n7]
-[tag_Name_dc7_n8]
-[tag_Name_dc7_n9]
-[tag_Name_dc7_n10]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n1
-tag_Name_dc7_n2
-tag_Name_dc7_n3
-tag_Name_dc7_n4
-tag_Name_dc7_n5
-tag_Name_dc7_n6
-tag_Name_dc7_n7
-tag_Name_dc7_n8
-tag_Name_dc7_n9
-tag_Name_dc7_n10
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc7_n1
-tag_Name_dc7_n2
-tag_Name_dc7_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc7_n4
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc7_n4
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc7_n4
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc7_n5
-tag_Name_dc7_n6
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc7_n7
-tag_Name_dc7_n8
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc7_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc7_n10
diff --git a/edge-baas-portal-1701-dc7/inventory-dc7-portal b/edge-baas-portal-1701-dc7/inventory-dc7-portal
deleted file mode 100644
index a0e784c..0000000
--- a/edge-baas-portal-1701-dc7/inventory-dc7-portal
+++ /dev/null
@@ -1,13 +0,0 @@
-[tag_Name_dc7_n21]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n21
-
-[devportal:children]
-dc-1-devportal
-
-[dc-1-devportal:children]
-tag_Name_dc7_n21
diff --git a/edge-ops-lab-1701-expansion/inventory-dc1 b/edge-ops-lab-1701-expansion/inventory-dc1
deleted file mode 120000
index 9fbca33..0000000
--- a/edge-ops-lab-1701-expansion/inventory-dc1
+++ /dev/null
@@ -1 +0,0 @@
-/Users/friasc/.ansible/inventory/edge-ops-lab-1701/inventory-dc1
\ No newline at end of file
diff --git a/edge-ops-lab/inventory-dc1 b/edge-ops-lab/inventory-dc1
deleted file mode 100644
index d309119..0000000
--- a/edge-ops-lab/inventory-dc1
+++ /dev/null
@@ -1,58 +0,0 @@
-[dc-1-ds]
-10.142.0.14
-10.142.0.[8:9]
-
-[dc-1-ms]
-10.142.0.5
-
-[dc-1-ui]
-10.142.0.5
-
-[dc-1-ldap]
-10.142.0.5
-
-[dc-1-rmp]
-10.142.0.[10:11]
-
-[dc-1-qpid]
-10.142.0.13
-10.142.0.7
-
-[dc-1-pg:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster]
-10.142.0.15
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-dc-1-ds
-dc-1-ms
-dc-1-ui
-dc-1-ldap
-dc-1-rmp
-dc-1-qpid
-dc-1-pg
-
-[ds:children]
-dc-1-ds
-
-[ms:children]
-dc-1-ms
-
-[ui:children]
-dc-1-ui
-
-[ldap:children]
-dc-1-ldap
-
-[rmp:children]
-dc-1-rmp
-
-[qpid:children]
-dc-1-qpid
-
-[pg:children]
-dc-1-pg
diff --git a/edgemicro-1601-dc1/ec2.ini b/edgemicro-1601-dc1/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/edgemicro-1601-dc1/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/edgemicro-1601-dc1/ec2.py b/edgemicro-1601-dc1/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/edgemicro-1601-dc1/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/edge-1601-aio/inventory b/edgemicro-1601-dc1/inventory-aio
similarity index 68%
rename from edge-1601-aio/inventory
rename to edgemicro-1601-dc1/inventory-aio
index 0bd7ed0..92f2907 100644
--- a/edge-1601-aio/inventory
+++ b/edgemicro-1601-dc1/inventory-aio
@@ -1,50 +1,51 @@
-[tag_Name_dc1_n1]
+[aio]
+0.0.0.0
 
 [planet:children]
 dc-1
 
 [dc-1:children]
-tag_Name_dc1_n1
+aio
 
 [ds:children]
 dc-1-ds
 
 [dc-1-ds:children]
-tag_Name_dc1_n1
+aio
 
 [ms:children]
 dc-1-ms
 
 [dc-1-ms:children]
-tag_Name_dc1_n1
+aio
 
 [ui:children]
 dc-1-ui
 
 [dc-1-ui:children]
-tag_Name_dc1_n1
+dc-1-ms
 
 [ldap:children]
 dc-1-ldap
 
 [dc-1-ldap:children]
-tag_Name_dc1_n1
+dc-1-ms
 
 [rmp:children]
 dc-1-rmp
 
 [dc-1-rmp:children]
-tag_Name_dc1_n1
+aio
 
 [qpid:children]
 dc-1-qpid
 
 [dc-1-qpid:children]
-tag_Name_dc1_n1
+aio
 
 [pg:children]
-dc-1-pg
+pg
 
 [dc-1-pg:children]
-tag_Name_dc1_n1
+aio
 
diff --git a/edgemicro-1601-dc1/inventory-dc2 b/edgemicro-1601-dc1/inventory-dc2
deleted file mode 100644
index 96e9880..0000000
--- a/edgemicro-1601-dc1/inventory-dc2
+++ /dev/null
@@ -1,78 +0,0 @@
-[tag_Name_dc2_n1]
-[tag_Name_dc2_n2]
-[tag_Name_dc2_n3]
-[tag_Name_dc2_n4]
-[tag_Name_dc2_n5]
-
-[tag_Name_dc2_n3:vars]
-zk_observer=true
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[ds:children]
-dc-1-ds
-
-[dc-1-ds:children]
-tag_Name_dc2_n1
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc2_n1
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-tag_Name_dc2_n1
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-tag_Name_dc2_n1
-
-[rmp:children]
-dc-1-rmp
-
-[dc-1-rmp:children]
-tag_Name_dc2_n2
-tag_Name_dc2_n3
-
-[qpid:children]
-dc-1-qpid
-
-[dc-1-qpid:children]
-tag_Name_dc2_n4
-tag_Name_dc2_n5
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc2_n4
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc2_n5
-
diff --git a/edgemicro-1601-dc1/inventory-edgemicro b/edgemicro-1601-dc1/inventory-edgemicro
index fc25bf9..fc923ea 100644
--- a/edgemicro-1601-dc1/inventory-edgemicro
+++ b/edgemicro-1601-dc1/inventory-edgemicro
@@ -1,4 +1,4 @@
 [tag_Name_dc2_n6]
 
 [micro:children]
-tag_Name_dc2_n6
+0.0.0.0
diff --git a/gcp-sample-inventory/gce.ini b/gcp-sample-inventory/gce.ini
deleted file mode 100644
index 27cbe3b..0000000
--- a/gcp-sample-inventory/gce.ini
+++ /dev/null
@@ -1,54 +0,0 @@
-#!/usr/bin/python
-# Copyright 2013 Google Inc.
-#
-# This file is part of Ansible
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-# The GCE inventory script has the following dependencies:
-#   1. A valid Google Cloud Platform account with Google Compute Engine
-#      enabled.  See https://cloud.google.com
-#   2. An OAuth2 Service Account flow should be enabled.  This will generate
-#      a private key file that the inventory script will use for API request
-#      authorization.  See https://developers.google.com/accounts/docs/OAuth2
-#   3. Convert the private key from PKCS12 to PEM format
-#      $ openssl pkcs12 -in pkey.pkcs12 -passin pass:notasecret \
-#      > -nodes -nocerts | openssl rsa -out pkey.pem
-#   4. The libcloud (>=0.13.3) python libray.  See http://libcloud.apache.org
-#
-# (See ansible/test/gce_tests.py comments for full install instructions)
-#
-# Author: Eric Johnson <erjohnso@google.com>
-
-[gce]
-# GCE Service Account configuration information can be stored in the
-# libcloud 'secrets.py' file.  Ideally, the 'secrets.py' file will already
-# exist in your PYTHONPATH and be picked up automatically with an import
-# statement in the inventory script.  However, you can specify an absolute
-# path to the secrets.py file with 'libcloud_secrets' parameter.
-libcloud_secrets =
-
-# If you are not going to use a 'secrets.py' file, you can set the necessary
-# authorization parameters here.
-gce_service_account_email_address = SERVICE_ACCOUNT_EMAIL_ADDRESS
-gce_service_account_pem_file_path = SERVICE_ACCOUNT_PRIVATE_SSH_KEY
-gce_project_id = GCP_PROJECT_ID
-
-[inventory]
-# The 'inventory_ip_type' parameter specifies whether 'ansible_ssh_host' should
-# contain the instance internal or external address. Values may be either
-# 'internal' or 'external'. If 'external' is specified but no external instance
-# address exists, the internal address will be used.
-# The INVENTORY_IP_TYPE environment variable will override this value.
-inventory_ip_type = external
diff --git a/gcp-sample-inventory/gce.py b/gcp-sample-inventory/gce.py
deleted file mode 100644
index ae6b502..0000000
--- a/gcp-sample-inventory/gce.py
+++ /dev/null
@@ -1,336 +0,0 @@
-#!/usr/bin/env python
-# Copyright 2013 Google Inc.
-#
-# This file is part of Ansible
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-'''
-GCE external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API requests
-Google Compute Engine via the libcloud library.  Full install/configuration
-instructions for the gce* modules can be found in the comments of
-ansible/test/gce_tests.py.
-
-When run against a specific host, this script returns the following variables
-based on the data obtained from the libcloud Node object:
- - gce_uuid
- - gce_id
- - gce_image
- - gce_machine_type
- - gce_private_ip
- - gce_public_ip
- - gce_name
- - gce_description
- - gce_status
- - gce_zone
- - gce_tags
- - gce_metadata
- - gce_network
-
-When run in --list mode, instances are grouped by the following categories:
- - zone:
-   zone group name examples are us-central1-b, europe-west1-a, etc.
- - instance tags:
-   An entry is created for each tag.  For example, if you have two instances
-   with a common tag called 'foo', they will both be grouped together under
-   the 'tag_foo' name.
- - network name:
-   the name of the network is appended to 'network_' (e.g. the 'default'
-   network will result in a group named 'network_default')
- - machine type
-   types follow a pattern like n1-standard-4, g1-small, etc.
- - running status:
-   group name prefixed with 'status_' (e.g. status_running, status_stopped,..)
- - image:
-   when using an ephemeral/scratch disk, this will be set to the image name
-   used when creating the instance (e.g. debian-7-wheezy-v20130816).  when
-   your instance was created with a root persistent disk it will be set to
-   'persistent_disk' since there is no current way to determine the image.
-
-Examples:
-  Execute uname on all instances in the us-central1-a zone
-  $ ansible -i gce.py us-central1-a -m shell -a "/bin/uname -a"
-
-  Use the GCE inventory script to print out instance specific information
-  $ contrib/inventory/gce.py --host my_instance
-
-Author: Eric Johnson <erjohnso@google.com>
-Contributors: Matt Hite <mhite@hotmail.com>
-Version: 0.0.2
-'''
-
-__requires__ = ['pycrypto>=2.6']
-try:
-    import pkg_resources
-except ImportError:
-    # Use pkg_resources to find the correct versions of libraries and set
-    # sys.path appropriately when there are multiversion installs.  We don't
-    # fail here as there is code that better expresses the errors where the
-    # library is used.
-    pass
-
-USER_AGENT_PRODUCT="Ansible-gce_inventory_plugin"
-USER_AGENT_VERSION="v2"
-
-import sys
-import os
-import argparse
-import ConfigParser
-
-import logging
-logging.getLogger('libcloud.common.google').addHandler(logging.NullHandler())
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-try:
-    from libcloud.compute.types import Provider
-    from libcloud.compute.providers import get_driver
-    _ = Provider.GCE
-except:
-    print("GCE inventory script requires libcloud >= 0.13")
-    sys.exit(1)
-
-
-class GceInventory(object):
-    def __init__(self):
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.config = self.get_config()
-        self.driver = self.get_gce_driver()
-        self.ip_type = self.get_inventory_options()
-        if self.ip_type:
-            self.ip_type = self.ip_type.lower()
-
-        # Just display data for specific host
-        if self.args.host:
-            print(self.json_format_dict(self.node_to_dict(
-                self.get_instance(self.args.host)),
-                pretty=self.args.pretty))
-            sys.exit(0)
-
-        # Otherwise, assume user wants all instances grouped
-        print(self.json_format_dict(self.group_instances(),
-                                    pretty=self.args.pretty))
-        sys.exit(0)
-
-    def get_config(self):
-        """
-        Populates a SafeConfigParser object with defaults and
-        attempts to read an .ini-style configuration from the filename
-        specified in GCE_INI_PATH. If the environment variable is
-        not present, the filename defaults to gce.ini in the current
-        working directory.
-        """
-        gce_ini_default_path = os.path.join(
-            os.path.dirname(os.path.realpath(__file__)), "gce.ini")
-        gce_ini_path = os.environ.get('GCE_INI_PATH', gce_ini_default_path)
-
-        # Create a ConfigParser.
-        # This provides empty defaults to each key, so that environment
-        # variable configuration (as opposed to INI configuration) is able
-        # to work.
-        config = ConfigParser.SafeConfigParser(defaults={
-            'gce_service_account_email_address': '',
-            'gce_service_account_pem_file_path': '',
-            'gce_project_id': '',
-            'libcloud_secrets': '',
-            'inventory_ip_type': '',
-        })
-        if 'gce' not in config.sections():
-            config.add_section('gce')
-        if 'inventory' not in config.sections():
-            config.add_section('inventory')
-
-        config.read(gce_ini_path)
-        return config
-
-    def get_inventory_options(self):
-        """Determine inventory options. Environment variables always
-        take precedence over configuration files."""
-        ip_type = self.config.get('inventory', 'inventory_ip_type')
-        # If the appropriate environment variables are set, they override
-        # other configuration
-        ip_type = os.environ.get('INVENTORY_IP_TYPE', ip_type)
-        return ip_type
-
-    def get_gce_driver(self):
-        """Determine the GCE authorization settings and return a
-        libcloud driver.
-        """
-        # Attempt to get GCE params from a configuration file, if one
-        # exists.
-        secrets_path = self.config.get('gce', 'libcloud_secrets')
-        secrets_found = False
-        try:
-            import secrets
-            args = list(getattr(secrets, 'GCE_PARAMS', []))
-            kwargs = getattr(secrets, 'GCE_KEYWORD_PARAMS', {})
-            secrets_found = True
-        except:
-            pass
-
-        if not secrets_found and secrets_path:
-            if not secrets_path.endswith('secrets.py'):
-                err = "Must specify libcloud secrets file as "
-                err += "/absolute/path/to/secrets.py"
-                print(err)
-                sys.exit(1)
-            sys.path.append(os.path.dirname(secrets_path))
-            try:
-                import secrets
-                args = list(getattr(secrets, 'GCE_PARAMS', []))
-                kwargs = getattr(secrets, 'GCE_KEYWORD_PARAMS', {})
-                secrets_found = True
-            except:
-                pass
-        if not secrets_found:
-            args = [
-                self.config.get('gce','gce_service_account_email_address'),
-                self.config.get('gce','gce_service_account_pem_file_path')
-            ]
-            kwargs = {'project': self.config.get('gce', 'gce_project_id')}
-
-        # If the appropriate environment variables are set, they override
-        # other configuration; process those into our args and kwargs.
-        args[0] = os.environ.get('GCE_EMAIL', args[0])
-        args[1] = os.environ.get('GCE_PEM_FILE_PATH', args[1])
-        kwargs['project'] = os.environ.get('GCE_PROJECT', kwargs['project'])
-
-        # Retrieve and return the GCE driver.
-        gce = get_driver(Provider.GCE)(*args, **kwargs)
-        gce.connection.user_agent_append(
-            '%s/%s' % (USER_AGENT_PRODUCT, USER_AGENT_VERSION),
-            )
-        return gce
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(
-            description='Produce an Ansible Inventory file based on GCE')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all information about an instance')
-        parser.add_argument('--pretty', action='store_true', default=False,
-                            help='Pretty format (default: False)')
-        self.args = parser.parse_args()
-
-
-    def node_to_dict(self, inst):
-        md = {}
-
-        if inst is None:
-            return {}
-
-        if inst.extra['metadata'].has_key('items'):
-            for entry in inst.extra['metadata']['items']:
-                md[entry['key']] = entry['value']
-
-        net = inst.extra['networkInterfaces'][0]['network'].split('/')[-1]
-        # default to exernal IP unless user has specified they prefer internal
-        if self.ip_type == 'internal':
-            ssh_host = inst.private_ips[0]
-        else:
-            ssh_host = inst.public_ips[0] if len(inst.public_ips) >= 1 else inst.private_ips[0]
-
-        return {
-            'gce_uuid': inst.uuid,
-            'gce_id': inst.id,
-            'gce_image': inst.image,
-            'gce_machine_type': inst.size,
-            'gce_private_ip': inst.private_ips[0],
-            'gce_public_ip': inst.public_ips[0] if len(inst.public_ips) >= 1 else None,
-            'gce_name': inst.name,
-            'gce_description': inst.extra['description'],
-            'gce_status': inst.extra['status'],
-            'gce_zone': inst.extra['zone'].name,
-            'gce_tags': inst.extra['tags'],
-            'gce_metadata': md,
-            'gce_network': net,
-            # Hosts don't have a public name, so we add an IP
-            'ansible_ssh_host': ssh_host
-        }
-
-    def get_instance(self, instance_name):
-        '''Gets details about a specific instance '''
-        try:
-            return self.driver.ex_get_node(instance_name)
-        except Exception as e:
-            return None
-
-    def group_instances(self):
-        '''Group all instances'''
-        groups = {}
-        meta = {}
-        meta["hostvars"] = {}
-
-        for node in self.driver.list_nodes():
-            name = node.name
-
-            meta["hostvars"][name] = self.node_to_dict(node)
-
-            zone = node.extra['zone'].name
-            if groups.has_key(zone): groups[zone].append(name)
-            else: groups[zone] = [name]
-
-            tags = node.extra['tags']
-            for t in tags:
-                if t.startswith('group-'):
-                    tag = t[6:]
-                else:
-                    tag = 'tag_%s' % t
-                if groups.has_key(tag): groups[tag].append(name)
-                else: groups[tag] = [name]
-
-            net = node.extra['networkInterfaces'][0]['network'].split('/')[-1]
-            net = 'network_%s' % net
-            if groups.has_key(net): groups[net].append(name)
-            else: groups[net] = [name]
-
-            machine_type = node.size
-            if groups.has_key(machine_type): groups[machine_type].append(name)
-            else: groups[machine_type] = [name]
-
-            image = node.image and node.image or 'persistent_disk'
-            if groups.has_key(image): groups[image].append(name)
-            else: groups[image] = [name]
-
-            status = node.extra['status']
-            stat = 'status_%s' % status.lower()
-            if groups.has_key(stat): groups[stat].append(name)
-            else: groups[stat] = [name]
-
-        groups["_meta"] = meta
-
-        return groups
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-GceInventory()
\ No newline at end of file
diff --git a/portal-1701-dc7/ec2.ini b/portal-1701-dc7/ec2.ini
deleted file mode 100644
index 36b3921..0000000
--- a/portal-1701-dc7/ec2.ini
+++ /dev/null
@@ -1,200 +0,0 @@
-# Ansible EC2 external inventory script settings
-#
-
-[ec2]
-
-# to talk to a private eucalyptus instance uncomment these lines
-# and edit edit eucalyptus_host to be the host name of your cloud controller
-#eucalyptus = True
-#eucalyptus_host = clc.cloud.domain.org
-
-# AWS regions to make calls to. Set this to 'all' to make request to all regions
-# in AWS and merge the results together. Alternatively, set this to a comma
-# separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-regions = all
-regions_exclude = us-gov-west-1,cn-north-1
-
-# When generating inventory, Ansible needs to know how to address a server.
-# Each EC2 instance has a lot of variables associated with it. Here is the list:
-#   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-# Below are 2 variables that are used as the address of a server:
-#   - destination_variable
-#   - vpc_destination_variable
-
-# This is the normal destination variable to use. If you are running Ansible
-# from outside EC2, then 'public_dns_name' makes the most sense. If you are
-# running Ansible from within EC2, then perhaps you want to use the internal
-# address, and should set this to 'private_dns_name'. The key of an EC2 tag
-# may optionally be used; however the boto instance variables hold precedence
-# in the event of a collision.
-destination_variable = public_dns_name
-
-# This allows you to override the inventory_name with an ec2 variable, instead
-# of using the destination_variable above. Addressing (aka ansible_ssh_host)
-# will still use destination_variable. Tags should be written as 'tag_TAGNAME'.
-#hostname_variable = tag_Name
-
-# For server inside a VPC, using DNS names may not make sense. When an instance
-# has 'subnet_id' set, this variable is used. If the subnet is public, setting
-# this to 'ip_address' will return the public IP address. For instances in a
-# private subnet, this should be set to 'private_ip_address', and Ansible must
-# be run from within EC2. The key of an EC2 tag may optionally be used; however
-# the boto instance variables hold precedence in the event of a collision.
-# WARNING: - instances that are in the private vpc, _without_ public ip address
-# will not be listed in the inventory until You set:
-# vpc_destination_variable = private_ip_address
-vpc_destination_variable = ip_address
-
-# The following two settings allow flexible ansible host naming based on a
-# python format string and a comma-separated list of ec2 tags.  Note that:
-#
-# 1) If the tags referenced are not present for some instances, empty strings
-#    will be substituted in the format string.
-# 2) This overrides both destination_variable and vpc_destination_variable.
-#
-#destination_format = {0}.{1}.example.com
-#destination_format_tags = Name,environment
-
-# To tag instances on EC2 with the resource records that point to them from
-# Route53, uncomment and set 'route53' to True.
-route53 = False
-
-# To exclude RDS instances from the inventory, uncomment and set to False.
-rds = False
-
-# To exclude ElastiCache instances from the inventory, uncomment and set to False.
-elasticache = False
-
-# Additionally, you can specify the list of zones to exclude looking up in
-# 'route53_excluded_zones' as a comma-separated list.
-# route53_excluded_zones = samplezone1.com, samplezone2.com
-
-# By default, only EC2 instances in the 'running' state are returned. Set
-# 'all_instances' to True to return all instances regardless of state.
-all_instances = True
-
-# By default, only EC2 instances in the 'running' state are returned. Specify
-# EC2 instance states to return as a comma-separated list. This
-# option is overriden when 'all_instances' is True.
-# instance_states = pending, running, shutting-down, terminated, stopping, stopped
-
-# By default, only RDS instances in the 'available' state are returned.  Set
-# 'all_rds_instances' to True return all RDS instances regardless of state.
-all_rds_instances = False
-
-# By default, only ElastiCache clusters and nodes in the 'available' state
-# are returned. Set 'all_elasticache_clusters' and/or 'all_elastic_nodes'
-# to True return all ElastiCache clusters and nodes, regardless of state.
-#
-# Note that all_elasticache_nodes only applies to listed clusters. That means
-# if you set all_elastic_clusters to false, no node will be return from
-# unavailable clusters, regardless of the state and to what you set for
-# all_elasticache_nodes.
-all_elasticache_replication_groups = False
-all_elasticache_clusters = False
-all_elasticache_nodes = False
-
-# API calls to EC2 are slow. For this reason, we cache the results of an API
-# call. Set this to the path you want cache files to be written to. Two files
-# will be written to this directory:
-#   - ansible-ec2.cache
-#   - ansible-ec2.index
-cache_path = ~/.ansible/tmp
-
-# The number of seconds a cache file is considered valid. After this many
-# seconds, a new API call will be made, and the cache file will be updated.
-# To disable the cache, set this value to 0
-cache_max_age = 300
-
-# Organize groups into a nested/hierarchy instead of a flat namespace.
-nested_groups = False
-
-# Replace - tags when creating groups to avoid issues with ansible
-replace_dash_in_groups = True
-
-# If set to true, any tag of the form "a,b,c" is expanded into a list
-# and the results are used to create additional tag_* inventory groups.
-expand_csv_tags = False
-
-# The EC2 inventory output can become very large. To manage its size,
-# configure which groups should be created.
-group_by_instance_id = True
-group_by_region = True
-group_by_availability_zone = True
-group_by_ami_id = True
-group_by_instance_type = True
-group_by_key_pair = True
-group_by_vpc_id = True
-group_by_security_group = True
-group_by_tag_keys = True
-group_by_tag_none = True
-group_by_route53_names = True
-group_by_rds_engine = False
-group_by_rds_parameter_group = False
-group_by_elasticache_engine = True
-group_by_elasticache_cluster = True
-group_by_elasticache_parameter_group = True
-group_by_elasticache_replication_group = True
-
-# If you only want to include hosts that match a certain regular expression
-# pattern_include = staging-*
-
-# If you want to exclude any hosts that match a certain regular expression
-# pattern_exclude = staging-*
-# Ansible EC2 external inventory script settings
-#
-
-##[ec2]
-##
-### to talk to a private eucalyptus instance uncomment these lines
-### and edit edit eucalyptus_host to be the host name of your cloud controller
-###eucalyptus = True
-###eucalyptus_host = clc.cloud.domain.org
-##
-### AWS regions to make calls to. Set this to 'all' to make request to all regions
-##
-### in AWS and merge the results together. Alternatively, set this to a comma
-### separated list of regions. E.g. 'us-east-1,us-west-1,us-west-2'
-##regions = all
-##regions_exclude = us-gov-west-1,cn-north-1
-##
-### When generating inventory, Ansible needs to know how to address a server.
-### Each EC2 instance has a lot of variables associated with it. Here is the list:
-###   http://docs.pythonboto.org/en/latest/ref/ec2.html#module-boto.ec2.instance
-### Below are 2 variables that are used as the address of a server:
-###   - destination_variable
-###   - vpc_destination_variable
-##
-### This is the normal destination variable to use. If you are running Ansible
-### from outside EC2, then 'public_dns_name' makes the most sense. If you are
-### running Ansible from within EC2, then perhaps you want to use the internal
-### address, and should set this to 'private_dns_name'. The key of an EC2 tag
-##...skipping...
-### pattern_include = staging-*
-##
-### If you want to exclude any hosts that match a certain regular expression
-### pattern_exclude = staging-*
-
-# Instance filters can be used to control which instances are retrieved for
-# inventory. For the full list of possible filters, please read the EC2 API
-# docs: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInstances.html#query-DescribeInstances-filters
-# Filters are key/value pairs separated by '=', to list multiple filters use
-# a list separated by commas. See examples below.
-
-# Retrieve only instances with (key=value) env=staging tag
-# instance_filters = tag:env=staging
-
-# Retrieve only instances with role=webservers OR role=dbservers tag
-# instance_filters = tag:role=webservers,tag:role=dbservers
-
-# Retrieve only t1.micro instances OR instances with tag env=staging
-# instance_filters = instance-type=t1.micro,tag:env=staging
-
-# You can use wildcards in filter values also. Below will list instances which
-# tag Name value matches webservers1*
-# (ex. webservers15, webservers1a, webservers123 etc)
-# instance_filters = tag:Name=webservers1*
-
-# A boto configuration profile may be used to separate out credentials
-# see http://boto.readthedocs.org/en/latest/boto_config_tut.html
-# boto_profile = some-boto-profile-name
diff --git a/portal-1701-dc7/ec2.py b/portal-1701-dc7/ec2.py
deleted file mode 100755
index f30958a..0000000
--- a/portal-1701-dc7/ec2.py
+++ /dev/null
@@ -1,1385 +0,0 @@
-#!/usr/bin/env python
-
-'''
-EC2 external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API request to
-AWS EC2 using the Boto library.
-
-NOTE: This script assumes Ansible is being executed where the environment
-variables needed for Boto have already been set:
-    export AWS_ACCESS_KEY_ID='AK123'
-    export AWS_SECRET_ACCESS_KEY='abc123'
-
-This script also assumes there is an ec2.ini file alongside it.  To specify a
-different path to ec2.ini, define the EC2_INI_PATH environment variable:
-
-    export EC2_INI_PATH=/path/to/my_ec2.ini
-
-If you're using eucalyptus you need to set the above variables and
-you need to define:
-
-    export EC2_URL=http://hostname_of_your_cc:port/services/Eucalyptus
-
-If you're using boto profiles (requires boto>=2.24.0) you can choose a profile
-using the --boto-profile command line argument (e.g. ec2.py --boto-profile prod) or using
-the AWS_PROFILE variable:
-
-    AWS_PROFILE=prod ansible-playbook -i ec2.py myplaybook.yml
-
-For more details, see: http://docs.pythonboto.org/en/latest/boto_config_tut.html
-
-When run against a specific host, this script returns the following variables:
- - ec2_ami_launch_index
- - ec2_architecture
- - ec2_association
- - ec2_attachTime
- - ec2_attachment
- - ec2_attachmentId
- - ec2_client_token
- - ec2_deleteOnTermination
- - ec2_description
- - ec2_deviceIndex
- - ec2_dns_name
- - ec2_eventsSet
- - ec2_group_name
- - ec2_hypervisor
- - ec2_id
- - ec2_image_id
- - ec2_instanceState
- - ec2_instance_type
- - ec2_ipOwnerId
- - ec2_ip_address
- - ec2_item
- - ec2_kernel
- - ec2_key_name
- - ec2_launch_time
- - ec2_monitored
- - ec2_monitoring
- - ec2_networkInterfaceId
- - ec2_ownerId
- - ec2_persistent
- - ec2_placement
- - ec2_platform
- - ec2_previous_state
- - ec2_private_dns_name
- - ec2_private_ip_address
- - ec2_publicIp
- - ec2_public_dns_name
- - ec2_ramdisk
- - ec2_reason
- - ec2_region
- - ec2_requester_id
- - ec2_root_device_name
- - ec2_root_device_type
- - ec2_security_group_ids
- - ec2_security_group_names
- - ec2_shutdown_state
- - ec2_sourceDestCheck
- - ec2_spot_instance_request_id
- - ec2_state
- - ec2_state_code
- - ec2_state_reason
- - ec2_status
- - ec2_subnet_id
- - ec2_tenancy
- - ec2_virtualization_type
- - ec2_vpc_id
-
-These variables are pulled out of a boto.ec2.instance object. There is a lack of
-consistency with variable spellings (camelCase and underscores) since this
-just loops through all variables the object exposes. It is preferred to use the
-ones with underscores when multiple exist.
-
-In addition, if an instance has AWS Tags associated with it, each tag is a new
-variable named:
- - ec2_tag_[Key] = [Value]
-
-Security groups are comma-separated in 'ec2_security_group_ids' and
-'ec2_security_group_names'.
-'''
-
-# (c) 2012, Peter Sankauskas
-#
-# This file is part of Ansible,
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-######################################################################
-
-import sys
-import os
-import argparse
-import re
-from time import time
-import boto
-from boto import ec2
-from boto import rds
-from boto import elasticache
-from boto import route53
-import six
-
-from six.moves import configparser
-from collections import defaultdict
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-
-class Ec2Inventory(object):
-
-    def _empty_inventory(self):
-        return {"_meta" : {"hostvars" : {}}}
-
-    def __init__(self):
-        ''' Main execution path '''
-
-        # Inventory grouped by instance IDs, tags, security groups, regions,
-        # and availability zones
-        self.inventory = self._empty_inventory()
-
-        # Index of hostname (address) to instance ID
-        self.index = {}
-
-        # Boto profile to use (if any)
-        self.boto_profile = None
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.read_settings()
-
-        # Make sure that profile_name is not passed at all if not set
-        # as pre 2.24 boto will fall over otherwise
-        if self.boto_profile:
-            if not hasattr(boto.ec2.EC2Connection, 'profile_name'):
-                self.fail_with_error("boto version must be >= 2.24 to use profile")
-
-        # Cache
-        if self.args.refresh_cache:
-            self.do_api_calls_update_cache()
-        elif not self.is_cache_valid():
-            self.do_api_calls_update_cache()
-
-        # Data to print
-        if self.args.host:
-            data_to_print = self.get_host_info()
-
-        elif self.args.list:
-            # Display list of instances for inventory
-            if self.inventory == self._empty_inventory():
-                data_to_print = self.get_inventory_from_cache()
-            else:
-                data_to_print = self.json_format_dict(self.inventory, True)
-
-        print(data_to_print)
-
-
-    def is_cache_valid(self):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + self.cache_max_age) > current_time:
-                if os.path.isfile(self.cache_path_index):
-                    return True
-
-        return False
-
-
-    def read_settings(self):
-        ''' Reads the settings from the ec2.ini file '''
-        if six.PY3:
-            config = configparser.ConfigParser()
-        else:
-            config = configparser.SafeConfigParser()
-        ec2_default_ini_path = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'ec2.ini')
-        ec2_ini_path = os.path.expanduser(os.path.expandvars(os.environ.get('EC2_INI_PATH', ec2_default_ini_path)))
-        config.read(ec2_ini_path)
-
-        # is eucalyptus?
-        self.eucalyptus_host = None
-        self.eucalyptus = False
-        if config.has_option('ec2', 'eucalyptus'):
-            self.eucalyptus = config.getboolean('ec2', 'eucalyptus')
-        if self.eucalyptus and config.has_option('ec2', 'eucalyptus_host'):
-            self.eucalyptus_host = config.get('ec2', 'eucalyptus_host')
-
-        # Regions
-        self.regions = []
-        configRegions = config.get('ec2', 'regions')
-        configRegions_exclude = config.get('ec2', 'regions_exclude')
-        if (configRegions == 'all'):
-            if self.eucalyptus_host:
-                self.regions.append(boto.connect_euca(host=self.eucalyptus_host).region.name)
-            else:
-                for regionInfo in ec2.regions():
-                    if regionInfo.name not in configRegions_exclude:
-                        self.regions.append(regionInfo.name)
-        else:
-            self.regions = configRegions.split(",")
-
-        # Destination addresses
-        self.destination_variable = config.get('ec2', 'destination_variable')
-        self.vpc_destination_variable = config.get('ec2', 'vpc_destination_variable')
-
-        if config.has_option('ec2', 'hostname_variable'):
-            self.hostname_variable = config.get('ec2', 'hostname_variable')
-        else:
-            self.hostname_variable = None
-
-        if config.has_option('ec2', 'destination_format') and \
-                config.has_option('ec2', 'destination_format_tags'):
-            self.destination_format = config.get('ec2', 'destination_format')
-            self.destination_format_tags = config.get('ec2', 'destination_format_tags').split(',')
-        else:
-            self.destination_format = None
-            self.destination_format_tags = None
-
-        # Route53
-        self.route53_enabled = config.getboolean('ec2', 'route53')
-        self.route53_excluded_zones = []
-        if config.has_option('ec2', 'route53_excluded_zones'):
-            self.route53_excluded_zones.extend(
-                    config.get('ec2', 'route53_excluded_zones', '').split(','))
-
-        # Include RDS instances?
-        self.rds_enabled = True
-        if config.has_option('ec2', 'rds'):
-            self.rds_enabled = config.getboolean('ec2', 'rds')
-
-        # Include ElastiCache instances?
-        self.elasticache_enabled = True
-        if config.has_option('ec2', 'elasticache'):
-            self.elasticache_enabled = config.getboolean('ec2', 'elasticache')
-
-        # Return all EC2 instances?
-        if config.has_option('ec2', 'all_instances'):
-            self.all_instances = config.getboolean('ec2', 'all_instances')
-        else:
-            self.all_instances = False
-
-        # Instance states to be gathered in inventory. Default is 'running'.
-        # Setting 'all_instances' to 'yes' overrides this option.
-        ec2_valid_instance_states = [
-            'pending',
-            'running',
-            'shutting-down',
-            'terminated',
-            'stopping',
-            'stopped'
-        ]
-        self.ec2_instance_states = []
-        if self.all_instances:
-            self.ec2_instance_states = ec2_valid_instance_states
-        elif config.has_option('ec2', 'instance_states'):
-            for instance_state in config.get('ec2', 'instance_states').split(','):
-                instance_state = instance_state.strip()
-                if instance_state not in ec2_valid_instance_states:
-                    continue
-                self.ec2_instance_states.append(instance_state)
-        else:
-            self.ec2_instance_states = ['running']
-
-        # Return all RDS instances? (if RDS is enabled)
-        if config.has_option('ec2', 'all_rds_instances') and self.rds_enabled:
-            self.all_rds_instances = config.getboolean('ec2', 'all_rds_instances')
-        else:
-            self.all_rds_instances = False
-
-        # Return all ElastiCache replication groups? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_replication_groups') and self.elasticache_enabled:
-            self.all_elasticache_replication_groups = config.getboolean('ec2', 'all_elasticache_replication_groups')
-        else:
-            self.all_elasticache_replication_groups = False
-
-        # Return all ElastiCache clusters? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_clusters') and self.elasticache_enabled:
-            self.all_elasticache_clusters = config.getboolean('ec2', 'all_elasticache_clusters')
-        else:
-            self.all_elasticache_clusters = False
-
-        # Return all ElastiCache nodes? (if ElastiCache is enabled)
-        if config.has_option('ec2', 'all_elasticache_nodes') and self.elasticache_enabled:
-            self.all_elasticache_nodes = config.getboolean('ec2', 'all_elasticache_nodes')
-        else:
-            self.all_elasticache_nodes = False
-
-        # boto configuration profile (prefer CLI argument)
-        self.boto_profile = self.args.boto_profile
-        if config.has_option('ec2', 'boto_profile') and not self.boto_profile:
-            self.boto_profile = config.get('ec2', 'boto_profile')
-
-        # Cache related
-        cache_dir = os.path.expanduser(config.get('ec2', 'cache_path'))
-        if self.boto_profile:
-            cache_dir = os.path.join(cache_dir, 'profile_' + self.boto_profile)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-
-        cache_name = 'ansible-ec2'
-        aws_profile = lambda: (self.boto_profile or
-                               os.environ.get('AWS_PROFILE') or
-                               os.environ.get('AWS_ACCESS_KEY_ID'))
-        if aws_profile():
-            cache_name = '%s-%s' % (cache_name, aws_profile())
-        self.cache_path_cache = cache_dir + "/%s.cache" % cache_name
-        self.cache_path_index = cache_dir + "/%s.index" % cache_name
-        self.cache_max_age = config.getint('ec2', 'cache_max_age')
-
-        if config.has_option('ec2', 'expand_csv_tags'):
-            self.expand_csv_tags = config.getboolean('ec2', 'expand_csv_tags')
-        else:
-            self.expand_csv_tags = False
-
-        # Configure nested groups instead of flat namespace.
-        if config.has_option('ec2', 'nested_groups'):
-            self.nested_groups = config.getboolean('ec2', 'nested_groups')
-        else:
-            self.nested_groups = False
-
-        # Replace dash or not in group names
-        if config.has_option('ec2', 'replace_dash_in_groups'):
-            self.replace_dash_in_groups = config.getboolean('ec2', 'replace_dash_in_groups')
-        else:
-            self.replace_dash_in_groups = True
-
-        # Configure which groups should be created.
-        group_by_options = [
-            'group_by_instance_id',
-            'group_by_region',
-            'group_by_availability_zone',
-            'group_by_ami_id',
-            'group_by_instance_type',
-            'group_by_key_pair',
-            'group_by_vpc_id',
-            'group_by_security_group',
-            'group_by_tag_keys',
-            'group_by_tag_none',
-            'group_by_route53_names',
-            'group_by_rds_engine',
-            'group_by_rds_parameter_group',
-            'group_by_elasticache_engine',
-            'group_by_elasticache_cluster',
-            'group_by_elasticache_parameter_group',
-            'group_by_elasticache_replication_group',
-        ]
-        for option in group_by_options:
-            if config.has_option('ec2', option):
-                setattr(self, option, config.getboolean('ec2', option))
-            else:
-                setattr(self, option, True)
-
-        # Do we need to just include hosts that match a pattern?
-        try:
-            pattern_include = config.get('ec2', 'pattern_include')
-            if pattern_include and len(pattern_include) > 0:
-                self.pattern_include = re.compile(pattern_include)
-            else:
-                self.pattern_include = None
-        except configparser.NoOptionError:
-            self.pattern_include = None
-
-        # Do we need to exclude hosts that match a pattern?
-        try:
-            pattern_exclude = config.get('ec2', 'pattern_exclude');
-            if pattern_exclude and len(pattern_exclude) > 0:
-                self.pattern_exclude = re.compile(pattern_exclude)
-            else:
-                self.pattern_exclude = None
-        except configparser.NoOptionError:
-            self.pattern_exclude = None
-
-        # Instance filters (see boto and EC2 API docs). Ignore invalid filters.
-        self.ec2_instance_filters = defaultdict(list)
-        if config.has_option('ec2', 'instance_filters'):
-
-            filters = [f for f in config.get('ec2', 'instance_filters').split(',') if f]
-
-            for instance_filter in filters:
-                instance_filter = instance_filter.strip()
-                if not instance_filter or '=' not in instance_filter:
-                    continue
-                filter_key, filter_value = [x.strip() for x in instance_filter.split('=', 1)]
-                if not filter_key:
-                    continue
-                self.ec2_instance_filters[filter_key].append(filter_value)
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(description='Produce an Ansible Inventory file based on EC2')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all the variables about a specific instance')
-        parser.add_argument('--refresh-cache', action='store_true', default=False,
-                            help='Force refresh of cache by making API requests to EC2 (default: False - use cache files)')
-        parser.add_argument('--profile', '--boto-profile', action='store', dest='boto_profile',
-                            help='Use boto profile for connections to EC2')
-        self.args = parser.parse_args()
-
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls to each region, and save data in cache files '''
-
-        if self.route53_enabled:
-            self.get_route53_records()
-
-        for region in self.regions:
-            self.get_instances_by_region(region)
-            if self.rds_enabled:
-                self.get_rds_instances_by_region(region)
-            if self.elasticache_enabled:
-                self.get_elasticache_clusters_by_region(region)
-                self.get_elasticache_replication_groups_by_region(region)
-
-        self.write_to_cache(self.inventory, self.cache_path_cache)
-        self.write_to_cache(self.index, self.cache_path_index)
-
-    def connect(self, region):
-        ''' create connection to api server'''
-        if self.eucalyptus:
-            conn = boto.connect_euca(host=self.eucalyptus_host)
-            conn.APIVersion = '2010-08-31'
-        else:
-            conn = self.connect_to_aws(ec2, region)
-        return conn
-
-    def boto_fix_security_token_in_profile(self, connect_args):
-        ''' monkey patch for boto issue boto/boto#2100 '''
-        profile = 'profile ' + self.boto_profile
-        if boto.config.has_option(profile, 'aws_security_token'):
-            connect_args['security_token'] = boto.config.get(profile, 'aws_security_token')
-        return connect_args
-
-    def connect_to_aws(self, module, region):
-        connect_args = {}
-
-        # only pass the profile name if it's set (as it is not supported by older boto versions)
-        if self.boto_profile:
-            connect_args['profile_name'] = self.boto_profile
-            self.boto_fix_security_token_in_profile(connect_args)
-
-        conn = module.connect_to_region(region, **connect_args)
-        # connect_to_region will fail "silently" by returning None if the region name is wrong or not supported
-        if conn is None:
-            self.fail_with_error("region name: %s likely not supported, or AWS is down.  connection to region failed." % region)
-        return conn
-
-    def get_instances_by_region(self, region):
-        ''' Makes an AWS EC2 API call to the list of instances in a particular
-        region '''
-
-        try:
-            conn = self.connect(region)
-            reservations = []
-            if self.ec2_instance_filters:
-                for filter_key, filter_values in self.ec2_instance_filters.items():
-                    reservations.extend(conn.get_all_instances(filters = { filter_key : filter_values }))
-            else:
-                reservations = conn.get_all_instances()
-
-            for reservation in reservations:
-                for instance in reservation.instances:
-                    self.add_instance(instance, region)
-
-        except boto.exception.BotoServerError as e:
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            else:
-                backend = 'Eucalyptus' if self.eucalyptus else 'AWS'
-                error = "Error connecting to %s backend.\n%s" % (backend, e.message)
-            self.fail_with_error(error, 'getting EC2 instances')
-
-    def get_rds_instances_by_region(self, region):
-        ''' Makes an AWS API call to the list of RDS instances in a particular
-        region '''
-
-        try:
-            conn = self.connect_to_aws(rds, region)
-            if conn:
-                marker = None
-                while True:
-                    instances = conn.get_all_dbinstances(marker=marker)
-                    marker = instances.marker
-                    for instance in instances:
-                        self.add_rds_instance(instance, region)
-                    if not marker:
-                        break
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS RDS is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting RDS instances')
-
-    def get_elasticache_clusters_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache clusters (with
-        nodes' info) in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                # show_cache_node_info = True
-                # because we also want nodes' information
-                response = conn.describe_cache_clusters(None, None, None, True)
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to CacheClusters or
-            # CacheNodes. Because of that wo can't make use of the get_list
-            # method in the AWSQueryConnection. Let's do the work manually
-            clusters = response['DescribeCacheClustersResponse']['DescribeCacheClustersResult']['CacheClusters']
-
-        except KeyError as e:
-            error = "ElastiCache query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for cluster in clusters:
-            self.add_elasticache_cluster(cluster, region)
-
-    def get_elasticache_replication_groups_by_region(self, region):
-        ''' Makes an AWS API call to the list of ElastiCache replication groups
-        in a particular region.'''
-
-        # ElastiCache boto module doesn't provide a get_all_intances method,
-        # that's why we need to call describe directly (it would be called by
-        # the shorthand method anyway...)
-        try:
-            conn = self.connect_to_aws(elasticache, region)
-            if conn:
-                response = conn.describe_replication_groups()
-
-        except boto.exception.BotoServerError as e:
-            error = e.reason
-
-            if e.error_code == 'AuthFailure':
-                error = self.get_auth_error_message()
-            if not e.reason == "Forbidden":
-                error = "Looks like AWS ElastiCache [Replication Groups] is down:\n%s" % e.message
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        try:
-            # Boto also doesn't provide wrapper classes to ReplicationGroups
-            # Because of that wo can't make use of the get_list method in the
-            # AWSQueryConnection. Let's do the work manually
-            replication_groups = response['DescribeReplicationGroupsResponse']['DescribeReplicationGroupsResult']['ReplicationGroups']
-
-        except KeyError as e:
-            error = "ElastiCache [Replication Groups] query to AWS failed (unexpected format)."
-            self.fail_with_error(error, 'getting ElastiCache clusters')
-
-        for replication_group in replication_groups:
-            self.add_elasticache_replication_group(replication_group, region)
-
-    def get_auth_error_message(self):
-        ''' create an informative error message if there is an issue authenticating'''
-        errors = ["Authentication error retrieving ec2 inventory."]
-        if None in [os.environ.get('AWS_ACCESS_KEY_ID'), os.environ.get('AWS_SECRET_ACCESS_KEY')]:
-            errors.append(' - No AWS_ACCESS_KEY_ID or AWS_SECRET_ACCESS_KEY environment vars found')
-        else:
-            errors.append(' - AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment vars found but may not be correct')
-
-        boto_paths = ['/etc/boto.cfg', '~/.boto', '~/.aws/credentials']
-        boto_config_found = list(p for p in boto_paths if os.path.isfile(os.path.expanduser(p)))
-        if len(boto_config_found) > 0:
-            errors.append(" - Boto configs found at '%s', but the credentials contained may not be correct" % ', '.join(boto_config_found))
-        else:
-            errors.append(" - No Boto config found at any expected location '%s'" % ', '.join(boto_paths))
-
-        return '\n'.join(errors)
-
-    def fail_with_error(self, err_msg, err_operation=None):
-        '''log an error to std err for ansible-playbook to consume and exit'''
-        if err_operation:
-            err_msg = 'ERROR: "{err_msg}", while: {err_operation}'.format(
-                    err_msg=err_msg, err_operation=err_operation)
-        sys.stderr.write(err_msg)
-        sys.exit(1)
-
-    def get_instance(self, region, instance_id):
-        conn = self.connect(region)
-
-        reservations = conn.get_all_instances([instance_id])
-        for reservation in reservations:
-            for instance in reservation.instances:
-                return instance
-
-    def add_instance(self, instance, region):
-        ''' Adds an instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only return instances with desired instance states
-        if instance.state not in self.ec2_instance_states:
-            return
-
-        # Select the best destination address
-        if self.destination_format and self.destination_format_tags:
-            dest = self.destination_format.format(*[ getattr(instance, 'tags').get(tag, '') for tag in self.destination_format_tags ])
-        elif instance.subnet_id:
-            dest = getattr(instance, self.vpc_destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.vpc_destination_variable, None)
-        else:
-            dest = getattr(instance, self.destination_variable, None)
-            if dest is None:
-                dest = getattr(instance, 'tags').get(self.destination_variable, None)
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-        else:
-            hostname = self.to_safe(hostname).lower()
-
-        # if we only want to include hosts that match a pattern, skip those that don't
-        if self.pattern_include and not self.pattern_include.match(hostname):
-            return
-
-        # if we need to exclude hosts that match a pattern, skip those
-        if self.pattern_exclude and self.pattern_exclude.match(hostname):
-            return
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.placement, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.placement)
-                self.push_group(self.inventory, 'zones', instance.placement)
-
-        # Inventory: Group by Amazon Machine Image (AMI) ID
-        if self.group_by_ami_id:
-            ami_id = self.to_safe(instance.image_id)
-            self.push(self.inventory, ami_id, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'images', ami_id)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_type)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by key pair
-        if self.group_by_key_pair and instance.key_name:
-            key_name = self.to_safe('key_' + instance.key_name)
-            self.push(self.inventory, key_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'keys', key_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                for group in instance.groups:
-                    key = self.to_safe("security_group_" + group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-        # Inventory: Group by tag keys
-        if self.group_by_tag_keys:
-            for k, v in instance.tags.items():
-                if self.expand_csv_tags and v and ',' in v:
-                    values = map(lambda x: x.strip(), v.split(','))
-                else:
-                    values = [v]
-
-                for v in values:
-                    if v:
-                        key = self.to_safe("tag_" + k + "=" + v)
-                    else:
-                        key = self.to_safe("tag_" + k)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'tags', self.to_safe("tag_" + k))
-                        if v:
-                            self.push_group(self.inventory, self.to_safe("tag_" + k), key)
-
-        # Inventory: Group by Route53 domain names if enabled
-        if self.route53_enabled and self.group_by_route53_names:
-            route53_names = self.get_instance_route53_names(instance)
-            for name in route53_names:
-                self.push(self.inventory, name, hostname)
-                if self.nested_groups:
-                    self.push_group(self.inventory, 'route53', name)
-
-        # Global Tag: instances without tags
-        if self.group_by_tag_none and len(instance.tags) == 0:
-            self.push(self.inventory, 'tag_none', hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'tags', 'tag_none')
-
-        # Global Tag: tag all EC2 instances
-        self.push(self.inventory, 'ec2', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-
-    def add_rds_instance(self, instance, region):
-        ''' Adds an RDS instance to the inventory and index, as long as it is
-        addressable '''
-
-        # Only want available instances unless all_rds_instances is True
-        if not self.all_rds_instances and instance.status != 'available':
-            return
-
-        # Select the best destination address
-        dest = instance.endpoint[0]
-
-        if not dest:
-            # Skip instances we cannot address (e.g. private VPC subnet)
-            return
-
-        # Set the inventory name
-        hostname = None
-        if self.hostname_variable:
-            if self.hostname_variable.startswith('tag_'):
-                hostname = instance.tags.get(self.hostname_variable[4:], None)
-            else:
-                hostname = getattr(instance, self.hostname_variable)
-
-        # If we can't get a nice hostname, use the destination address
-        if not hostname:
-            hostname = dest
-
-        hostname = self.to_safe(hostname).lower()
-
-        # Add to index
-        self.index[hostname] = [region, instance.id]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[instance.id] = [hostname]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', instance.id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, instance.availability_zone, hostname)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, instance.availability_zone)
-                self.push_group(self.inventory, 'zones', instance.availability_zone)
-
-        # Inventory: Group by instance type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + instance.instance_class)
-            self.push(self.inventory, type_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC
-        if self.group_by_vpc_id and instance.subnet_group and instance.subnet_group.vpc_id:
-            vpc_id_name = self.to_safe('vpc_id_' + instance.subnet_group.vpc_id)
-            self.push(self.inventory, vpc_id_name, hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'vpcs', vpc_id_name)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-            try:
-                if instance.security_group:
-                    key = self.to_safe("security_group_" + instance.security_group.name)
-                    self.push(self.inventory, key, hostname)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-            except AttributeError:
-                self.fail_with_error('\n'.join(['Package boto seems a bit older.',
-                                                'Please upgrade boto >= 2.3.0.']))
-
-
-        # Inventory: Group by engine
-        if self.group_by_rds_engine:
-            self.push(self.inventory, self.to_safe("rds_" + instance.engine), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_engines', self.to_safe("rds_" + instance.engine))
-
-        # Inventory: Group by parameter group
-        if self.group_by_rds_parameter_group:
-            self.push(self.inventory, self.to_safe("rds_parameter_group_" + instance.parameter_group.name), hostname)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'rds_parameter_groups', self.to_safe("rds_parameter_group_" + instance.parameter_group.name))
-
-        # Global Tag: all RDS instances
-        self.push(self.inventory, 'rds', hostname)
-
-        self.inventory["_meta"]["hostvars"][hostname] = self.get_host_info_dict_from_instance(instance)
-        self.inventory["_meta"]["hostvars"][hostname]['ansible_ssh_host'] = dest
-
-    def add_elasticache_cluster(self, cluster, region):
-        ''' Adds an ElastiCache cluster to the inventory and index, as long as
-        it's nodes are addressable '''
-
-        # Only want available clusters unless all_elasticache_clusters is True
-        if not self.all_elasticache_clusters and cluster['CacheClusterStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        if 'ConfigurationEndpoint' in cluster and cluster['ConfigurationEndpoint']:
-            # Memcached cluster
-            dest = cluster['ConfigurationEndpoint']['Address']
-            is_redis = False
-        else:
-            # Redis sigle node cluster
-            # Because all Redis clusters are single nodes, we'll merge the
-            # info from the cluster with info about the node
-            dest = cluster['CacheNodes'][0]['Endpoint']['Address']
-            is_redis = True
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, cluster['CacheClusterId']]
-
-        # Inventory: Group by instance ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[cluster['CacheClusterId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', cluster['CacheClusterId'])
-
-        # Inventory: Group by region
-        if self.group_by_region and not is_redis:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone and not is_redis:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type and not is_redis:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group and not is_redis:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine and not is_redis:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe(cluster['Engine']))
-
-        # Inventory: Group by parameter group
-        if self.group_by_elasticache_parameter_group:
-            self.push(self.inventory, self.to_safe("elasticache_parameter_group_" + cluster['CacheParameterGroup']['CacheParameterGroupName']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_parameter_groups', self.to_safe(cluster['CacheParameterGroup']['CacheParameterGroupName']))
-
-        # Inventory: Group by replication group
-        if self.group_by_elasticache_replication_group and 'ReplicationGroupId' in cluster and cluster['ReplicationGroupId']:
-            self.push(self.inventory, self.to_safe("elasticache_replication_group_" + cluster['ReplicationGroupId']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_replication_groups', self.to_safe(cluster['ReplicationGroupId']))
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_clusters', cluster['CacheClusterId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(cluster)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-        # Add the nodes
-        for node in cluster['CacheNodes']:
-            self.add_elasticache_node(node, cluster, region)
-
-    def add_elasticache_node(self, node, cluster, region):
-        ''' Adds an ElastiCache node to the inventory and index, as long as
-        it is addressable '''
-
-        # Only want available nodes unless all_elasticache_nodes is True
-        if not self.all_elasticache_nodes and node['CacheNodeStatus'] != 'available':
-            return
-
-        # Select the best destination address
-        dest = node['Endpoint']['Address']
-
-        if not dest:
-            # Skip nodes we cannot address (e.g. private VPC subnet)
-            return
-
-        node_id = self.to_safe(cluster['CacheClusterId'] + '_' + node['CacheNodeId'])
-
-        # Add to index
-        self.index[dest] = [region, node_id]
-
-        # Inventory: Group by node ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[node_id] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', node_id)
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone
-        if self.group_by_availability_zone:
-            self.push(self.inventory, cluster['PreferredAvailabilityZone'], dest)
-            if self.nested_groups:
-                if self.group_by_region:
-                    self.push_group(self.inventory, region, cluster['PreferredAvailabilityZone'])
-                self.push_group(self.inventory, 'zones', cluster['PreferredAvailabilityZone'])
-
-        # Inventory: Group by node type
-        if self.group_by_instance_type:
-            type_name = self.to_safe('type_' + cluster['CacheNodeType'])
-            self.push(self.inventory, type_name, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'types', type_name)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for ElastiCache)
-
-        # Inventory: Group by security group
-        if self.group_by_security_group:
-
-            # Check for the existence of the 'SecurityGroups' key and also if
-            # this key has some value. When the cluster is not placed in a SG
-            # the query can return None here and cause an error.
-            if 'SecurityGroups' in cluster and cluster['SecurityGroups'] is not None:
-                for security_group in cluster['SecurityGroups']:
-                    key = self.to_safe("security_group_" + security_group['SecurityGroupId'])
-                    self.push(self.inventory, key, dest)
-                    if self.nested_groups:
-                        self.push_group(self.inventory, 'security_groups', key)
-
-        # Inventory: Group by engine
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, self.to_safe("elasticache_" + cluster['Engine']), dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', self.to_safe("elasticache_" + cluster['Engine']))
-
-        # Inventory: Group by parameter group (done at cluster level)
-
-        # Inventory: Group by replication group (done at cluster level)
-
-        # Inventory: Group by ElastiCache Cluster
-        if self.group_by_elasticache_cluster:
-            self.push(self.inventory, self.to_safe("elasticache_cluster_" + cluster['CacheClusterId']), dest)
-
-        # Global Tag: all ElastiCache nodes
-        self.push(self.inventory, 'elasticache_nodes', dest)
-
-        host_info = self.get_host_info_dict_from_describe_dict(node)
-
-        if dest in self.inventory["_meta"]["hostvars"]:
-            self.inventory["_meta"]["hostvars"][dest].update(host_info)
-        else:
-            self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def add_elasticache_replication_group(self, replication_group, region):
-        ''' Adds an ElastiCache replication group to the inventory and index '''
-
-        # Only want available clusters unless all_elasticache_replication_groups is True
-        if not self.all_elasticache_replication_groups and replication_group['Status'] != 'available':
-            return
-
-        # Select the best destination address (PrimaryEndpoint)
-        dest = replication_group['NodeGroups'][0]['PrimaryEndpoint']['Address']
-
-        if not dest:
-            # Skip clusters we cannot address (e.g. private VPC subnet)
-            return
-
-        # Add to index
-        self.index[dest] = [region, replication_group['ReplicationGroupId']]
-
-        # Inventory: Group by ID (always a group of 1)
-        if self.group_by_instance_id:
-            self.inventory[replication_group['ReplicationGroupId']] = [dest]
-            if self.nested_groups:
-                self.push_group(self.inventory, 'instances', replication_group['ReplicationGroupId'])
-
-        # Inventory: Group by region
-        if self.group_by_region:
-            self.push(self.inventory, region, dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'regions', region)
-
-        # Inventory: Group by availability zone (doesn't apply to replication groups)
-
-        # Inventory: Group by node type (doesn't apply to replication groups)
-
-        # Inventory: Group by VPC (information not available in the current
-        # AWS API version for replication groups
-
-        # Inventory: Group by security group (doesn't apply to replication groups)
-        # Check this value in cluster level
-
-        # Inventory: Group by engine (replication groups are always Redis)
-        if self.group_by_elasticache_engine:
-            self.push(self.inventory, 'elasticache_redis', dest)
-            if self.nested_groups:
-                self.push_group(self.inventory, 'elasticache_engines', 'redis')
-
-        # Global Tag: all ElastiCache clusters
-        self.push(self.inventory, 'elasticache_replication_groups', replication_group['ReplicationGroupId'])
-
-        host_info = self.get_host_info_dict_from_describe_dict(replication_group)
-
-        self.inventory["_meta"]["hostvars"][dest] = host_info
-
-    def get_route53_records(self):
-        ''' Get and store the map of resource records to domain names that
-        point to them. '''
-
-        r53_conn = route53.Route53Connection()
-        all_zones = r53_conn.get_zones()
-
-        route53_zones = [ zone for zone in all_zones if zone.name[:-1]
-                          not in self.route53_excluded_zones ]
-
-        self.route53_records = {}
-
-        for zone in route53_zones:
-            rrsets = r53_conn.get_all_rrsets(zone.id)
-
-            for record_set in rrsets:
-                record_name = record_set.name
-
-                if record_name.endswith('.'):
-                    record_name = record_name[:-1]
-
-                for resource in record_set.resource_records:
-                    self.route53_records.setdefault(resource, set())
-                    self.route53_records[resource].add(record_name)
-
-
-    def get_instance_route53_names(self, instance):
-        ''' Check if an instance is referenced in the records we have from
-        Route53. If it is, return the list of domain names pointing to said
-        instance. If nothing points to it, return an empty list. '''
-
-        instance_attributes = [ 'public_dns_name', 'private_dns_name',
-                                'ip_address', 'private_ip_address' ]
-
-        name_list = set()
-
-        for attrib in instance_attributes:
-            try:
-                value = getattr(instance, attrib)
-            except AttributeError:
-                continue
-
-            if value in self.route53_records:
-                name_list.update(self.route53_records[value])
-
-        return list(name_list)
-
-    def get_host_info_dict_from_instance(self, instance):
-        instance_vars = {}
-        for key in vars(instance):
-            value = getattr(instance, key)
-            key = self.to_safe('ec2_' + key)
-
-            # Handle complex types
-            # state/previous_state changed to properties in boto in https://github.com/boto/boto/commit/a23c379837f698212252720d2af8dec0325c9518
-            if key == 'ec2__state':
-                instance_vars['ec2_state'] = instance.state or ''
-                instance_vars['ec2_state_code'] = instance.state_code
-            elif key == 'ec2__previous_state':
-                instance_vars['ec2_previous_state'] = instance.previous_state or ''
-                instance_vars['ec2_previous_state_code'] = instance.previous_state_code
-            elif type(value) in [int, bool]:
-                instance_vars[key] = value
-            elif isinstance(value, six.string_types):
-                instance_vars[key] = value.strip()
-            elif type(value) == type(None):
-                instance_vars[key] = ''
-            elif key == 'ec2_region':
-                instance_vars[key] = value.name
-            elif key == 'ec2__placement':
-                instance_vars['ec2_placement'] = value.zone
-            elif key == 'ec2_tags':
-                for k, v in value.items():
-                    if self.expand_csv_tags and ',' in v:
-                        v = map(lambda x: x.strip(), v.split(','))
-                    key = self.to_safe('ec2_tag_' + k)
-                    instance_vars[key] = v
-            elif key == 'ec2_groups':
-                group_ids = []
-                group_names = []
-                for group in value:
-                    group_ids.append(group.id)
-                    group_names.append(group.name)
-                instance_vars["ec2_security_group_ids"] = ','.join([str(i) for i in group_ids])
-                instance_vars["ec2_security_group_names"] = ','.join([str(i) for i in group_names])
-            else:
-                pass
-                # TODO Product codes if someone finds them useful
-                #print key
-                #print type(value)
-                #print value
-
-        return instance_vars
-
-    def get_host_info_dict_from_describe_dict(self, describe_dict):
-        ''' Parses the dictionary returned by the API call into a flat list
-            of parameters. This method should be used only when 'describe' is
-            used directly because Boto doesn't provide specific classes. '''
-
-        # I really don't agree with prefixing everything with 'ec2'
-        # because EC2, RDS and ElastiCache are different services.
-        # I'm just following the pattern used until now to not break any
-        # compatibility.
-
-        host_info = {}
-        for key in describe_dict:
-            value = describe_dict[key]
-            key = self.to_safe('ec2_' + self.uncammelize(key))
-
-            # Handle complex types
-
-            # Target: Memcached Cache Clusters
-            if key == 'ec2_configuration_endpoint' and value:
-                host_info['ec2_configuration_endpoint_address'] = value['Address']
-                host_info['ec2_configuration_endpoint_port'] = value['Port']
-
-            # Target: Cache Nodes and Redis Cache Clusters (single node)
-            if key == 'ec2_endpoint' and value:
-                host_info['ec2_endpoint_address'] = value['Address']
-                host_info['ec2_endpoint_port'] = value['Port']
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_node_groups' and value:
-                host_info['ec2_endpoint_address'] = value[0]['PrimaryEndpoint']['Address']
-                host_info['ec2_endpoint_port'] = value[0]['PrimaryEndpoint']['Port']
-                replica_count = 0
-                for node in value[0]['NodeGroupMembers']:
-                    if node['CurrentRole'] == 'primary':
-                        host_info['ec2_primary_cluster_address'] = node['ReadEndpoint']['Address']
-                        host_info['ec2_primary_cluster_port'] = node['ReadEndpoint']['Port']
-                        host_info['ec2_primary_cluster_id'] = node['CacheClusterId']
-                    elif node['CurrentRole'] == 'replica':
-                        host_info['ec2_replica_cluster_address_'+ str(replica_count)] = node['ReadEndpoint']['Address']
-                        host_info['ec2_replica_cluster_port_'+ str(replica_count)] = node['ReadEndpoint']['Port']
-                        host_info['ec2_replica_cluster_id_'+ str(replica_count)] = node['CacheClusterId']
-                        replica_count += 1
-
-            # Target: Redis Replication Groups
-            if key == 'ec2_member_clusters' and value:
-                host_info['ec2_member_clusters'] = ','.join([str(i) for i in value])
-
-            # Target: All Cache Clusters
-            elif key == 'ec2_cache_parameter_group':
-                host_info["ec2_cache_node_ids_to_reboot"] = ','.join([str(i) for i in value['CacheNodeIdsToReboot']])
-                host_info['ec2_cache_parameter_group_name'] = value['CacheParameterGroupName']
-                host_info['ec2_cache_parameter_apply_status'] = value['ParameterApplyStatus']
-
-            # Target: Almost everything
-            elif key == 'ec2_security_groups':
-
-                # Skip if SecurityGroups is None
-                # (it is possible to have the key defined but no value in it).
-                if value is not None:
-                    sg_ids = []
-                    for sg in value:
-                        sg_ids.append(sg['SecurityGroupId'])
-                    host_info["ec2_security_group_ids"] = ','.join([str(i) for i in sg_ids])
-
-            # Target: Everything
-            # Preserve booleans and integers
-            elif type(value) in [int, bool]:
-                host_info[key] = value
-
-            # Target: Everything
-            # Sanitize string values
-            elif isinstance(value, six.string_types):
-                host_info[key] = value.strip()
-
-            # Target: Everything
-            # Replace None by an empty string
-            elif type(value) == type(None):
-                host_info[key] = ''
-
-            else:
-                # Remove non-processed complex types
-                pass
-
-        return host_info
-
-    def get_host_info(self):
-        ''' Get variables about a specific host '''
-
-        if len(self.index) == 0:
-            # Need to load index from cache
-            self.load_index_from_cache()
-
-        if not self.args.host in self.index:
-            # try updating the cache
-            self.do_api_calls_update_cache()
-            if not self.args.host in self.index:
-                # host might not exist anymore
-                return self.json_format_dict({}, True)
-
-        (region, instance_id) = self.index[self.args.host]
-
-        instance = self.get_instance(region, instance_id)
-        return self.json_format_dict(self.get_host_info_dict_from_instance(instance), True)
-
-    def push(self, my_dict, key, element):
-        ''' Push an element onto an array that may not have been defined in
-        the dict '''
-        group_info = my_dict.setdefault(key, [])
-        if isinstance(group_info, dict):
-            host_list = group_info.setdefault('hosts', [])
-            host_list.append(element)
-        else:
-            group_info.append(element)
-
-    def push_group(self, my_dict, key, element):
-        ''' Push a group as a child of another group. '''
-        parent_group = my_dict.setdefault(key, {})
-        if not isinstance(parent_group, dict):
-            parent_group = my_dict[key] = {'hosts': parent_group}
-        child_groups = parent_group.setdefault('children', [])
-        if element not in child_groups:
-            child_groups.append(element)
-
-    def get_inventory_from_cache(self):
-        ''' Reads the inventory from the cache file and returns it as a JSON
-        object '''
-
-        cache = open(self.cache_path_cache, 'r')
-        json_inventory = cache.read()
-        return json_inventory
-
-
-    def load_index_from_cache(self):
-        ''' Reads the index from the cache file sets self.index '''
-
-        cache = open(self.cache_path_index, 'r')
-        json_index = cache.read()
-        self.index = json.loads(json_index)
-
-
-    def write_to_cache(self, data, filename):
-        ''' Writes data in JSON format to a file '''
-
-        json_data = self.json_format_dict(data, True)
-        cache = open(filename, 'w')
-        cache.write(json_data)
-        cache.close()
-
-    def uncammelize(self, key):
-        temp = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', key)
-        return re.sub('([a-z0-9])([A-Z])', r'\1_\2', temp).lower()
-
-    def to_safe(self, word):
-        ''' Converts 'bad' characters in a string to underscores so they can be used as Ansible groups '''
-        regex = "[^A-Za-z0-9\_"
-        if not self.replace_dash_in_groups:
-            regex += "\-"
-        return re.sub(regex + "]", "_", word)
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-
-# Run the script
-Ec2Inventory()
diff --git a/portal-1701-dc7/inventory b/portal-1701-dc7/inventory
deleted file mode 100644
index fbdd439..0000000
--- a/portal-1701-dc7/inventory
+++ /dev/null
@@ -1,43 +0,0 @@
-[tag_Name_dc7_n21]
-[tag_Name_dc7_n22]
-[tag_Name_dc7_n9]
-[tag_Name_dc7_n10]
-[tag_Name_dc7_n4]
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-tag_Name_dc7_n21
-tag_Name_dc7_n22
-tag_Name_dc7_n9
-tag_Name_dc7_n10
-tag_Name_dc7_n4
-
-[ms:children]
-dc-1-ms
-
-[dc-1-ms:children]
-tag_Name_dc7_n4
-
-[portal:children]
-tag_Name_dc7_n21
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[dc-1-pgmaster:children]
-tag_Name_dc7_n9
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dc-1-pgstandby:children]
-tag_Name_dc7_n10
diff --git a/edge-1601-aio/inventory b/sample-aio/inventory-aio
similarity index 68%
copy from edge-1601-aio/inventory
copy to sample-aio/inventory-aio
index 0bd7ed0..92f2907 100644
--- a/edge-1601-aio/inventory
+++ b/sample-aio/inventory-aio
@@ -1,50 +1,51 @@
-[tag_Name_dc1_n1]
+[aio]
+0.0.0.0
 
 [planet:children]
 dc-1
 
 [dc-1:children]
-tag_Name_dc1_n1
+aio
 
 [ds:children]
 dc-1-ds
 
 [dc-1-ds:children]
-tag_Name_dc1_n1
+aio
 
 [ms:children]
 dc-1-ms
 
 [dc-1-ms:children]
-tag_Name_dc1_n1
+aio
 
 [ui:children]
 dc-1-ui
 
 [dc-1-ui:children]
-tag_Name_dc1_n1
+dc-1-ms
 
 [ldap:children]
 dc-1-ldap
 
 [dc-1-ldap:children]
-tag_Name_dc1_n1
+dc-1-ms
 
 [rmp:children]
 dc-1-rmp
 
 [dc-1-rmp:children]
-tag_Name_dc1_n1
+aio
 
 [qpid:children]
 dc-1-qpid
 
 [dc-1-qpid:children]
-tag_Name_dc1_n1
+aio
 
 [pg:children]
-dc-1-pg
+pg
 
 [dc-1-pg:children]
-tag_Name_dc1_n1
+aio
 
diff --git a/sample-edge-dc-1/baas-dc1 b/sample-baas-dc1/baas-dc1
similarity index 100%
rename from sample-edge-dc-1/baas-dc1
rename to sample-baas-dc1/baas-dc1
diff --git a/sample-edge-dc-1/devportal-dc1 b/sample-devportal-dc1/devportal-dc1
similarity index 100%
rename from sample-edge-dc-1/devportal-dc1
rename to sample-devportal-dc1/devportal-dc1
diff --git a/edge-1601-dc2/ec2.ini b/sample-ec2/ec2.ini
similarity index 100%
rename from edge-1601-dc2/ec2.ini
rename to sample-ec2/ec2.ini
diff --git a/edge-1601-dc2/ec2.py b/sample-ec2/ec2.py
similarity index 100%
rename from edge-1601-dc2/ec2.py
rename to sample-ec2/ec2.py
diff --git a/sample-edge-dc-1-dc-2/gce.py b/sample-edge-dc-1-dc-2/gce.py
deleted file mode 100755
index 9a0cef0..0000000
--- a/sample-edge-dc-1-dc-2/gce.py
+++ /dev/null
@@ -1,508 +0,0 @@
-#!/usr/bin/env python
-# Copyright 2013 Google Inc.
-#
-# This file is part of Ansible
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-'''
-GCE external inventory script
-=================================
-
-Generates inventory that Ansible can understand by making API requests
-Google Compute Engine via the libcloud library.  Full install/configuration
-instructions for the gce* modules can be found in the comments of
-ansible/test/gce_tests.py.
-
-When run against a specific host, this script returns the following variables
-based on the data obtained from the libcloud Node object:
- - gce_uuid
- - gce_id
- - gce_image
- - gce_machine_type
- - gce_private_ip
- - gce_public_ip
- - gce_name
- - gce_description
- - gce_status
- - gce_zone
- - gce_tags
- - gce_metadata
- - gce_network
- - gce_subnetwork
-
-When run in --list mode, instances are grouped by the following categories:
- - zone:
-   zone group name examples are us-central1-b, europe-west1-a, etc.
- - instance tags:
-   An entry is created for each tag.  For example, if you have two instances
-   with a common tag called 'foo', they will both be grouped together under
-   the 'tag_foo' name.
- - network name:
-   the name of the network is appended to 'network_' (e.g. the 'default'
-   network will result in a group named 'network_default')
- - machine type
-   types follow a pattern like n1-standard-4, g1-small, etc.
- - running status:
-   group name prefixed with 'status_' (e.g. status_running, status_stopped,..)
- - image:
-   when using an ephemeral/scratch disk, this will be set to the image name
-   used when creating the instance (e.g. debian-7-wheezy-v20130816).  when
-   your instance was created with a root persistent disk it will be set to
-   'persistent_disk' since there is no current way to determine the image.
-
-Examples:
-  Execute uname on all instances in the us-central1-a zone
-  $ ansible -i gce.py us-central1-a -m shell -a "/bin/uname -a"
-
-  Use the GCE inventory script to print out instance specific information
-  $ contrib/inventory/gce.py --host my_instance
-
-Author: Eric Johnson <erjohnso@google.com>
-Contributors: Matt Hite <mhite@hotmail.com>, Tom Melendez <supertom@google.com>
-Version: 0.0.3
-'''
-
-try:
-    import pkg_resources
-except ImportError:
-    # Use pkg_resources to find the correct versions of libraries and set
-    # sys.path appropriately when there are multiversion installs.  We don't
-    # fail here as there is code that better expresses the errors where the
-    # library is used.
-    pass
-
-USER_AGENT_PRODUCT = "Ansible-gce_inventory_plugin"
-USER_AGENT_VERSION = "v2"
-
-import sys
-import os
-import argparse
-
-from time import time
-
-if sys.version_info >= (3, 0):
-    import configparser
-else:
-    import ConfigParser as configparser
-
-import logging
-logging.getLogger('libcloud.common.google').addHandler(logging.NullHandler())
-
-try:
-    import json
-except ImportError:
-    import simplejson as json
-
-try:
-    from libcloud.compute.types import Provider
-    from libcloud.compute.providers import get_driver
-    _ = Provider.GCE
-except:
-    sys.exit("GCE inventory script requires libcloud >= 0.13")
-
-
-class CloudInventoryCache(object):
-    def __init__(self, cache_name='ansible-cloud-cache', cache_path='/tmp',
-                 cache_max_age=300):
-        cache_dir = os.path.expanduser(cache_path)
-        if not os.path.exists(cache_dir):
-            os.makedirs(cache_dir)
-        self.cache_path_cache = os.path.join(cache_dir, cache_name)
-
-        self.cache_max_age = cache_max_age
-
-    def is_valid(self, max_age=None):
-        ''' Determines if the cache files have expired, or if it is still valid '''
-
-        if max_age is None:
-            max_age = self.cache_max_age
-
-        if os.path.isfile(self.cache_path_cache):
-            mod_time = os.path.getmtime(self.cache_path_cache)
-            current_time = time()
-            if (mod_time + max_age) > current_time:
-                return True
-
-        return False
-
-    def get_all_data_from_cache(self, filename=''):
-        ''' Reads the JSON inventory from the cache file. Returns Python dictionary. '''
-
-        data = ''
-        if not filename:
-            filename = self.cache_path_cache
-        with open(filename, 'r') as cache:
-            data = cache.read()
-        return json.loads(data)
-
-    def write_to_cache(self, data, filename=''):
-        ''' Writes data to file as JSON.  Returns True. '''
-        if not filename:
-            filename = self.cache_path_cache
-        json_data = json.dumps(data)
-        with open(filename, 'w') as cache:
-            cache.write(json_data)
-        return True
-
-
-class GceInventory(object):
-    def __init__(self):
-        # Cache object
-        self.cache = None
-        # dictionary containing inventory read from disk
-        self.inventory = {}
-
-        # Read settings and parse CLI arguments
-        self.parse_cli_args()
-        self.config = self.get_config()
-        self.driver = self.get_gce_driver()
-        self.ip_type = self.get_inventory_options()
-        if self.ip_type:
-            self.ip_type = self.ip_type.lower()
-
-        # Cache management
-        start_inventory_time = time()
-        cache_used = False
-        if self.args.refresh_cache or not self.cache.is_valid():
-            self.do_api_calls_update_cache()
-        else:
-            self.load_inventory_from_cache()
-            cache_used = True
-            self.inventory['_meta']['stats'] = {'use_cache': True}
-        self.inventory['_meta']['stats'] = {
-            'inventory_load_time': time() - start_inventory_time,
-            'cache_used': cache_used
-        }
-
-        # Just display data for specific host
-        if self.args.host:
-            print(self.json_format_dict(
-                self.inventory['_meta']['hostvars'][self.args.host],
-                pretty=self.args.pretty))
-        else:
-            # Otherwise, assume user wants all instances grouped
-            zones = self.parse_env_zones()
-            print(self.json_format_dict(self.inventory,
-                                        pretty=self.args.pretty))
-        sys.exit(0)
-
-    def get_config(self):
-        """
-        Reads the settings from the gce.ini file.
-
-        Populates a SafeConfigParser object with defaults and
-        attempts to read an .ini-style configuration from the filename
-        specified in GCE_INI_PATH. If the environment variable is
-        not present, the filename defaults to gce.ini in the current
-        working directory.
-        """
-        gce_ini_default_path = os.path.join(
-            os.path.dirname(os.path.realpath(__file__)), "gce.ini")
-        gce_ini_path = os.environ.get('GCE_INI_PATH', gce_ini_default_path)
-
-        # Create a ConfigParser.
-        # This provides empty defaults to each key, so that environment
-        # variable configuration (as opposed to INI configuration) is able
-        # to work.
-        config = configparser.SafeConfigParser(defaults={
-            'gce_service_account_email_address': '',
-            'gce_service_account_pem_file_path': '',
-            'gce_project_id': '',
-            'gce_zone': '',
-            'libcloud_secrets': '',
-            'inventory_ip_type': '',
-            'cache_path': '~/.ansible/tmp',
-            'cache_max_age': '300'
-        })
-        if 'gce' not in config.sections():
-            config.add_section('gce')
-        if 'inventory' not in config.sections():
-            config.add_section('inventory')
-        if 'cache' not in config.sections():
-            config.add_section('cache')
-
-        config.read(gce_ini_path)
-
-        #########
-        # Section added for processing ini settings
-        #########
-
-        # Set the instance_states filter based on config file options
-        self.instance_states = []
-        if config.has_option('gce', 'instance_states'):
-            states = config.get('gce', 'instance_states')
-            # Ignore if instance_states is an empty string.
-            if states:
-                self.instance_states = states.split(',')
-
-        # Caching
-        cache_path = config.get('cache', 'cache_path')
-        cache_max_age = config.getint('cache', 'cache_max_age')
-        # TOOD(supertom): support project-specific caches
-        cache_name = 'ansible-gce.cache'
-        self.cache = CloudInventoryCache(cache_path=cache_path,
-                                         cache_max_age=cache_max_age,
-                                         cache_name=cache_name)
-        return config
-
-    def get_inventory_options(self):
-        """Determine inventory options. Environment variables always
-        take precedence over configuration files."""
-        ip_type = self.config.get('inventory', 'inventory_ip_type')
-        # If the appropriate environment variables are set, they override
-        # other configuration
-        ip_type = os.environ.get('INVENTORY_IP_TYPE', ip_type)
-        return ip_type
-
-    def get_gce_driver(self):
-        """Determine the GCE authorization settings and return a
-        libcloud driver.
-        """
-        # Attempt to get GCE params from a configuration file, if one
-        # exists.
-        secrets_path = self.config.get('gce', 'libcloud_secrets')
-        secrets_found = False
-
-        try:
-            import secrets
-            args = list(secrets.GCE_PARAMS)
-            kwargs = secrets.GCE_KEYWORD_PARAMS
-            secrets_found = True
-        except:
-            pass
-
-        if not secrets_found and secrets_path:
-            if not secrets_path.endswith('secrets.py'):
-                err = "Must specify libcloud secrets file as "
-                err += "/absolute/path/to/secrets.py"
-                sys.exit(err)
-            sys.path.append(os.path.dirname(secrets_path))
-            try:
-                import secrets
-                args = list(getattr(secrets, 'GCE_PARAMS', []))
-                kwargs = getattr(secrets, 'GCE_KEYWORD_PARAMS', {})
-                secrets_found = True
-            except:
-                pass
-
-        if not secrets_found:
-            args = [
-                self.config.get('gce', 'gce_service_account_email_address'),
-                self.config.get('gce', 'gce_service_account_pem_file_path')
-            ]
-            kwargs = {'project': self.config.get('gce', 'gce_project_id'),
-                      'datacenter': self.config.get('gce', 'gce_zone')}
-
-        # If the appropriate environment variables are set, they override
-        # other configuration; process those into our args and kwargs.
-        args[0] = os.environ.get('GCE_EMAIL', args[0])
-        args[1] = os.environ.get('GCE_PEM_FILE_PATH', args[1])
-        args[1] = os.environ.get('GCE_CREDENTIALS_FILE_PATH', args[1])
-
-        kwargs['project'] = os.environ.get('GCE_PROJECT', kwargs['project'])
-        kwargs['datacenter'] = os.environ.get('GCE_ZONE', kwargs['datacenter'])
-
-        # Retrieve and return the GCE driver.
-        gce = get_driver(Provider.GCE)(*args, **kwargs)
-        gce.connection.user_agent_append(
-            '%s/%s' % (USER_AGENT_PRODUCT, USER_AGENT_VERSION),
-        )
-        return gce
-
-    def parse_env_zones(self):
-        '''returns a list of comma separated zones parsed from the GCE_ZONE environment variable.
-        If provided, this will be used to filter the results of the grouped_instances call'''
-        import csv
-        reader = csv.reader([os.environ.get('GCE_ZONE', "")], skipinitialspace=True)
-        zones = [r for r in reader]
-        return [z for z in zones[0]]
-
-    def parse_cli_args(self):
-        ''' Command line argument processing '''
-
-        parser = argparse.ArgumentParser(
-            description='Produce an Ansible Inventory file based on GCE')
-        parser.add_argument('--list', action='store_true', default=True,
-                            help='List instances (default: True)')
-        parser.add_argument('--host', action='store',
-                            help='Get all information about an instance')
-        parser.add_argument('--pretty', action='store_true', default=False,
-                            help='Pretty format (default: False)')
-        parser.add_argument(
-            '--refresh-cache', action='store_true', default=False,
-            help='Force refresh of cache by making API requests (default: False - use cache files)')
-        self.args = parser.parse_args()
-
-    def node_to_dict(self, inst):
-        md = {}
-
-        if inst is None:
-            return {}
-
-        if 'items' in inst.extra['metadata']:
-            for entry in inst.extra['metadata']['items']:
-                md[entry['key']] = entry['value']
-
-        net = inst.extra['networkInterfaces'][0]['network'].split('/')[-1]
-        subnet = None
-        if 'subnetwork' in inst.extra['networkInterfaces'][0]:
-            subnet = inst.extra['networkInterfaces'][0]['subnetwork'].split('/')[-1]
-        # default to exernal IP unless user has specified they prefer internal
-        if self.ip_type == 'internal':
-            ssh_host = inst.private_ips[0]
-        else:
-            ssh_host = inst.public_ips[0] if len(inst.public_ips) >= 1 else inst.private_ips[0]
-
-        return {
-            'gce_uuid': inst.uuid,
-            'gce_id': inst.id,
-            'gce_image': inst.image,
-            'gce_machine_type': inst.size,
-            'gce_private_ip': inst.private_ips[0],
-            'gce_public_ip': inst.public_ips[0] if len(inst.public_ips) >= 1 else None,
-            'gce_name': inst.name,
-            'gce_description': inst.extra['description'],
-            'gce_status': inst.extra['status'],
-            'gce_zone': inst.extra['zone'].name,
-            'gce_tags': inst.extra['tags'],
-            'gce_metadata': md,
-            'gce_network': net,
-            'gce_subnetwork': subnet,
-            # Hosts don't have a public name, so we add an IP
-            'ansible_ssh_host': ssh_host
-        }
-
-    def load_inventory_from_cache(self):
-        ''' Loads inventory from JSON on disk. '''
-
-        try:
-            self.inventory = self.cache.get_all_data_from_cache()
-            hosts = self.inventory['_meta']['hostvars']
-        except Exception as e:
-            print(
-                "Invalid inventory file %s.  Please rebuild with -refresh-cache option."
-                % (self.cache.cache_path_cache))
-            raise
-
-    def do_api_calls_update_cache(self):
-        ''' Do API calls and save data in cache. '''
-        zones = self.parse_env_zones()
-        data = self.group_instances(zones)
-        self.cache.write_to_cache(data)
-        self.inventory = data
-
-    def list_nodes(self):
-        all_nodes = []
-        params, more_results = {'maxResults': 500}, True
-        while more_results:
-            self.driver.connection.gce_params = params
-            all_nodes.extend(self.driver.list_nodes())
-            more_results = 'pageToken' in params
-        return all_nodes
-
-    def group_instances(self, zones=None):
-        '''Group all instances'''
-        groups = {}
-        meta = {}
-        meta["hostvars"] = {}
-
-        for node in self.list_nodes():
-
-            # This check filters on the desired instance states defined in the
-            # config file with the instance_states config option.
-            #
-            # If the instance_states list is _empty_ then _ALL_ states are returned.
-            #
-            # If the instance_states list is _populated_ then check the current
-            # state against the instance_states list
-            if self.instance_states and not node.extra['status'] in self.instance_states:
-                continue
-
-            name = node.name
-
-            meta["hostvars"][name] = self.node_to_dict(node)
-
-            zone = node.extra['zone'].name
-
-            # To avoid making multiple requests per zone
-            # we list all nodes and then filter the results
-            if zones and zone not in zones:
-                continue
-
-            if zone in groups:
-                groups[zone].append(name)
-            else:
-                groups[zone] = [name]
-
-            tags = node.extra['tags']
-            for t in tags:
-                if t.startswith('group-'):
-                    tag = t[6:]
-                else:
-                    tag = 'tag_%s' % t
-                if tag in groups:
-                    groups[tag].append(name)
-                else:
-                    groups[tag] = [name]
-
-            net = node.extra['networkInterfaces'][0]['network'].split('/')[-1]
-            net = 'network_%s' % net
-            if net in groups:
-                groups[net].append(name)
-            else:
-                groups[net] = [name]
-
-            machine_type = node.size
-            if machine_type in groups:
-                groups[machine_type].append(name)
-            else:
-                groups[machine_type] = [name]
-
-            image = node.image and node.image or 'persistent_disk'
-            if image in groups:
-                groups[image].append(name)
-            else:
-                groups[image] = [name]
-
-            status = node.extra['status']
-            stat = 'status_%s' % status.lower()
-            if stat in groups:
-                groups[stat].append(name)
-            else:
-                groups[stat] = [name]
-
-            for private_ip in node.private_ips:
-                groups[private_ip] = [name]
-
-            if len(node.public_ips) >= 1:
-                for public_ip in node.public_ips:
-                    groups[public_ip] = [name]
-
-        groups["_meta"] = meta
-
-        return groups
-
-    def json_format_dict(self, data, pretty=False):
-        ''' Converts a dict to a JSON object and dumps it as a formatted
-        string '''
-
-        if pretty:
-            return json.dumps(data, sort_keys=True, indent=2)
-        else:
-            return json.dumps(data)
-
-# Run the script
-if __name__ == '__main__':
-    GceInventory()
diff --git a/sample-edge-dc-1-dc-2/inventory-dc1 b/sample-edge-dc-1-dc-2/inventory-dc1
deleted file mode 100644
index 37ccaae..0000000
--- a/sample-edge-dc-1-dc-2/inventory-dc1
+++ /dev/null
@@ -1,101 +0,0 @@
-[cfmirror]
-cf-000
-
-[dc-1-edge]
-cf-00[1:9]
-cf-010
-
-[dc-1-ds]
-cf-00[1:3]
-
-[dc-1-ms]
-cf-004
-
-[dc-1-rmp]
-cf-00[5:6]
-
-[dc-1-qpid]
-cf-00[7:8]
-
-[dc-1-pgmaster]
-cf-009
-
-[dc-1-pgstandby]
-cf-010
-
-[dc-1-dp-ui]
-cf-011
-
-[dc-1-dp-db]
-cf-012
-
-[telegraf]
-cf-00[1:9]
-cf-01[1:2]
-
-[grafana]
-cf-013
-
-[influxdb]
-cf-014
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-dc-1-edge
-cfmirror
-dp
-grafana
-influxdb
-
-[edge:children]
-dc-1-edge
-
-[ms:children]
-dc-1-ms
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-dc-1-ms
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-dc-1-ms
-
-[ds:children]
-dc-1-ds
-
-[rmp:children]
-dc-1-rmp
-
-[qpid:children]
-dc-1-qpid
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dp:children]
-dp-ui
-dp-db
-
-[dp-ui:children]
-dc-1-dp-ui
-
-[dp-db:children]
-dc-1-dp-db
-
diff --git a/sample-edge-dc-1-dc-2/inventory-dc2 b/sample-edge-dc-1-dc-2/inventory-dc2
deleted file mode 100644
index 37ccaae..0000000
--- a/sample-edge-dc-1-dc-2/inventory-dc2
+++ /dev/null
@@ -1,101 +0,0 @@
-[cfmirror]
-cf-000
-
-[dc-1-edge]
-cf-00[1:9]
-cf-010
-
-[dc-1-ds]
-cf-00[1:3]
-
-[dc-1-ms]
-cf-004
-
-[dc-1-rmp]
-cf-00[5:6]
-
-[dc-1-qpid]
-cf-00[7:8]
-
-[dc-1-pgmaster]
-cf-009
-
-[dc-1-pgstandby]
-cf-010
-
-[dc-1-dp-ui]
-cf-011
-
-[dc-1-dp-db]
-cf-012
-
-[telegraf]
-cf-00[1:9]
-cf-01[1:2]
-
-[grafana]
-cf-013
-
-[influxdb]
-cf-014
-
-[planet:children]
-dc-1
-
-[dc-1:children]
-dc-1-edge
-cfmirror
-dp
-grafana
-influxdb
-
-[edge:children]
-dc-1-edge
-
-[ms:children]
-dc-1-ms
-
-[ui:children]
-dc-1-ui
-
-[dc-1-ui:children]
-dc-1-ms
-
-[ldap:children]
-dc-1-ldap
-
-[dc-1-ldap:children]
-dc-1-ms
-
-[ds:children]
-dc-1-ds
-
-[rmp:children]
-dc-1-rmp
-
-[qpid:children]
-dc-1-qpid
-
-[pg:children]
-dc-1-pg
-
-[dc-1-pg:children]
-dc-1-pgmaster
-dc-1-pgstandby
-
-[pgmaster:children]
-dc-1-pgmaster
-
-[pgstandby:children]
-dc-1-pgstandby
-
-[dp:children]
-dp-ui
-dp-db
-
-[dp-ui:children]
-dc-1-dp-ui
-
-[dp-db:children]
-dc-1-dp-db
-
diff --git a/sample-edge-dc-1/gce.ini b/sample-edge-dc-1/gce.ini
deleted file mode 100644
index 0c60b00..0000000
--- a/sample-edge-dc-1/gce.ini
+++ /dev/null
@@ -1,55 +0,0 @@
-#!/usr/bin/python
-# Copyright 2013 Google Inc.
-#
-# This file is part of Ansible
-#
-# Ansible is free software: you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation, either version 3 of the License, or
-# (at your option) any later version.
-#
-# Ansible is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
-
-# The GCE inventory script has the following dependencies:
-#   1. A valid Google Cloud Platform account with Google Compute Engine
-#      enabled.  See https://cloud.google.com
-#   2. An OAuth2 Service Account flow should be enabled.  This will generate
-#      a private key file that the inventory script will use for API request
-#      authorization.  See https://developers.google.com/accounts/docs/OAuth2
-#   3. Convert the private key from PKCS12 to PEM format
-#      $ openssl pkcs12 -in pkey.pkcs12 -passin pass:notasecret \
-#      > -nodes -nocerts | openssl rsa -out pkey.pem
-#   4. The libcloud (>=0.13.3) python libray.  See http://libcloud.apache.org
-#
-# (See ansible/test/gce_tests.py comments for full install instructions)
-#
-# Author: Eric Johnson <erjohnso@google.com>
-
-[gce]
-# GCE Service Account configuration information can be stored in the
-# libcloud 'secrets.py' file.  Ideally, the 'secrets.py' file will already
-# exist in your PYTHONPATH and be picked up automatically with an import
-# statement in the inventory script.  However, you can specify an absolute
-# path to the secrets.py file with 'libcloud_secrets' parameter.
-libcloud_secrets = ""
-
-# If you are not going to use a 'secrets.py' file, you can set the necessary
-# authorization parameters here.
-gce_service_account_email_address = 200499658291-compute@developer.gserviceaccount.com
-gce_service_account_pem_file_path = /home/friasc/.ansible/access/default-service-account.json
-gce_project_id = edge-ops-lab
-gce_zone = us-east1-b
-
-[inventory]
-# The 'inventory_ip_type' parameter specifies whether 'ansible_ssh_host' should
-# contain the instance internal or external address. Values may be either
-# 'internal' or 'external'. If 'external' is specified but no external instance
-# address exists, the internal address will be used.
-# The INVENTORY_IP_TYPE environment variable will override this value.
-inventory_ip_type = internal
diff --git a/sample-edge-dc-1/edge-dc1 b/sample-edge-one-datacenter/edge-dc1
similarity index 73%
copy from sample-edge-dc-1/edge-dc1
copy to sample-edge-one-datacenter/edge-dc1
index d8f43c8..ca57eca 100644
--- a/sample-edge-dc-1/edge-dc1
+++ b/sample-edge-one-datacenter/edge-dc1
@@ -5,6 +5,14 @@
 [dc-1-ds]
 cf-00[1:3]
 
+# Setting an observer Zookeeper node
+# cf-003 zk_observer=true
+
+# Setting Cassandra with Rack Aware Settings
+# cf-001 rack=1,1
+# cf-002 rack=1,2
+# cf-003 rack=1,3
+
 [dc-1-ms]
 cf-004
 
@@ -31,6 +39,13 @@
 
 [dc-1:children]
 dc-1-edge
+dc-1-ds
+dc-1-ms
+dc-1-ldap
+dc-1-ui
+dc-1-rmp
+dc-1-qpid
+dc-1-pg
 
 [edge:children]
 dc-1-edge
diff --git a/sample-edge-dc-1/edge-dc1 b/sample-edge-two-datacenters/edge-dc1
similarity index 90%
rename from sample-edge-dc-1/edge-dc1
rename to sample-edge-two-datacenters/edge-dc1
index d8f43c8..a82f4a4 100644
--- a/sample-edge-dc-1/edge-dc1
+++ b/sample-edge-two-datacenters/edge-dc1
@@ -31,6 +31,13 @@
 
 [dc-1:children]
 dc-1-edge
+dc-1-ds
+dc-1-ms
+dc-1-ldap
+dc-1-ui
+dc-1-rmp
+dc-1-qpid
+dc-1-pg
 
 [edge:children]
 dc-1-edge
diff --git a/edge-ops-lab-1701-expansion/inventory-dc2 b/sample-edge-two-datacenters/edge-dc2
similarity index 62%
rename from edge-ops-lab-1701-expansion/inventory-dc2
rename to sample-edge-two-datacenters/edge-dc2
index 4c77b3b..9cc447e 100644
--- a/edge-ops-lab-1701-expansion/inventory-dc2
+++ b/sample-edge-two-datacenters/edge-dc2
@@ -1,42 +1,47 @@
+[dc-2-edge]
+cf-00[1:9]
+cf-010
+
 [dc-2-ds]
-10.142.0.[16:17]
-10.142.0.18 zk_observer=true
+cf-00[1:2]
+cf-003 zk_observer=true
 
 [dc-2-ms]
-10.142.0.19
-
-[dc-2-ui]
-10.142.0.19
+cf-004
 
 [dc-2-ldap]
-10.142.0.19
+cf-004
+
+[dc-2-ui]
+cf-004
 
 [dc-2-rmp]
-10.142.0.[20:21]
+cf-00[5:6]
 
 [dc-2-qpid]
-10.142.0.[23:24]
+cf-00[7:8]
 
-[dc-2-pg:children]
-dc-2-pgstandby
+[dc-2-pgmaster]
+cf-009
 
 [dc-2-pgstandby]
-10.142.0.22
+cf-010
 
 [planet:children]
 dc-2
 
 [dc-2:children]
+dc-2-edge
 dc-2-ds
 dc-2-ms
-dc-2-ui
 dc-2-ldap
+dc-2-ui
 dc-2-rmp
 dc-2-qpid
 dc-2-pg
 
-[ds:children]
-dc-2-ds
+[edge:children]
+dc-2-edge
 
 [ms:children]
 dc-2-ms
@@ -44,9 +49,18 @@
 [ui:children]
 dc-2-ui
 
+[dc-2-ui:children]
+dc-2-ms
+
 [ldap:children]
 dc-2-ldap
 
+[dc-2-ldap:children]
+dc-2-ms
+
+[ds:children]
+dc-2-ds
+
 [rmp:children]
 dc-2-rmp
 
@@ -56,8 +70,12 @@
 [pg:children]
 dc-2-pg
 
-[pgstandby:children]
+[dc-2-pg:children]
+dc-2-pgmaster
 dc-2-pgstandby
 
 [pgmaster:children]
-dc-1-pg
+dc-2-pgmaster
+
+[pgstandby:children]
+dc-2-pgstandby
diff --git a/sample-edge-dc-1-dc-2/gce.ini b/sample-gcp/gce.ini
similarity index 90%
rename from sample-edge-dc-1-dc-2/gce.ini
rename to sample-gcp/gce.ini
index 0c60b00..43af53b 100644
--- a/sample-edge-dc-1-dc-2/gce.ini
+++ b/sample-gcp/gce.ini
@@ -41,10 +41,10 @@
 
 # If you are not going to use a 'secrets.py' file, you can set the necessary
 # authorization parameters here.
-gce_service_account_email_address = 200499658291-compute@developer.gserviceaccount.com
-gce_service_account_pem_file_path = /home/friasc/.ansible/access/default-service-account.json
-gce_project_id = edge-ops-lab
-gce_zone = us-east1-b
+gce_service_account_email_address = sample-account-compute@developer.gserviceaccount.com
+gce_service_account_pem_file_path = ~/.apigee-secure/default-service-account.json
+gce_project_id = your-gce-project-id
+gce_zone = your-gce-zone
 
 [inventory]
 # The 'inventory_ip_type' parameter specifies whether 'ansible_ssh_host' should
diff --git a/sample-edge-dc-1/gce.py b/sample-gcp/gce.py
similarity index 100%
rename from sample-edge-dc-1/gce.py
rename to sample-gcp/gce.py
diff --git a/sample-edge-dc-1/mirror b/sample-mirror/mirror
similarity index 100%
rename from sample-edge-dc-1/mirror
rename to sample-mirror/mirror
diff --git a/sample-edge-dc-1/monitoring-dc1 b/sample-monitoring-dc1/monitoring-dc1
similarity index 100%
rename from sample-edge-dc-1/monitoring-dc1
rename to sample-monitoring-dc1/monitoring-dc1
