From 02836f37160cd8082fe2c30e880d74927e9885f8 Mon Sep 17 00:00:00 2001 From: Mark Chappell Date: Sun, 17 Oct 2021 11:01:37 +0200 Subject: [PATCH] ec2_eip tagging support (#332) ec2_eip tagging support SUMMARY Add support for tagging EIPs on creation. Todo: EIP Tagging Tests Retry decorator Note: While it's now possible to pass tagging information into the association call this was only added Dec 2020 so won't work for most folks. ISSUE TYPE Feature Pull Request COMPONENT NAME ec2_eip ec2_eip_info ADDITIONAL INFORMATION fixes: #331 Reviewed-by: Rick Mendes Reviewed-by: None --- changelogs/fragments/332-ec2_eip-tagging.yml | 4 + plugins/modules/ec2_eip.py | 22 +- plugins/modules/ec2_eip_info.py | 15 +- .../targets/ec2_eip/defaults/main.yml | 1 + .../integration/targets/ec2_eip/meta/main.yml | 2 +- .../targets/ec2_eip/tasks/main.yml | 212 +++++++++++++++--- 6 files changed, 222 insertions(+), 34 deletions(-) create mode 100644 changelogs/fragments/332-ec2_eip-tagging.yml diff --git a/changelogs/fragments/332-ec2_eip-tagging.yml b/changelogs/fragments/332-ec2_eip-tagging.yml new file mode 100644 index 00000000000..c9621b405fe --- /dev/null +++ b/changelogs/fragments/332-ec2_eip-tagging.yml @@ -0,0 +1,4 @@ +minor_changes: +- ec2_eip - added support for tagging EIPs (https://github.com/ansible-collections/community.aws/pull/332). +- ec2_eip_info - added support for tagging EIPs (https://github.com/ansible-collections/community.aws/pull/332). +- ec2_eip_info - added automatic retries for common temporary API failures (https://github.com/ansible-collections/community.aws/pull/332). diff --git a/plugins/modules/ec2_eip.py b/plugins/modules/ec2_eip.py index 927d31551b7..e38e941661f 100644 --- a/plugins/modules/ec2_eip.py +++ b/plugins/modules/ec2_eip.py @@ -64,6 +64,16 @@ network interface or instance to be re-associated with the specified instance or interface. default: false type: bool + tags: + description: A dictionary of tags to apply to the EIP. + type: dict + version_added: 2.1.0 + purge_tags: + description: Whether the I(tags) argument should cause tags not in the + dictionary to be removed. + default: True + type: bool + version_added: 2.1.0 tag_name: description: - When I(reuse_existing_ip_allowed=true), supplement with this option to only reuse @@ -227,6 +237,7 @@ from ansible_collections.amazon.aws.plugins.module_utils.core import is_boto3_error_code from ansible_collections.amazon.aws.plugins.module_utils.ec2 import AWSRetry from ansible_collections.amazon.aws.plugins.module_utils.ec2 import ansible_dict_to_boto3_filter_list +from ansible_collections.amazon.aws.plugins.module_utils.ec2 import ensure_ec2_tags def associate_ip_and_device(ec2, module, address, private_ip_address, device_id, allow_reassociation, check_mode, is_instance=True): @@ -247,7 +258,7 @@ def associate_ip_and_device(ec2, module, address, private_ip_address, device_id, params['AllocationId'] = address['AllocationId'] else: params['PublicIp'] = address['PublicIp'] - res = ec2.associate_address(**params) + res = ec2.associate_address(aws_retry=True, **params) except (botocore.exceptions.BotoCoreError, botocore.exceptions.ClientError) as e: msg = "Couldn't associate Elastic IP address with instance '{0}'".format(device_id) module.fail_json_aws(e, msg=msg) @@ -535,6 +546,8 @@ def main(): allow_reassociation=dict(type='bool', default=False), wait_timeout=dict(type='int', removed_at_date='2022-06-01', removed_from_collection='community.aws'), private_ip_address=dict(), + tags=dict(required=False, type='dict'), + purge_tags=dict(required=False, type='bool', default=True), tag_name=dict(), tag_value=dict(), public_ipv4_pool=dict() @@ -563,6 +576,8 @@ def main(): tag_name = module.params.get('tag_name') tag_value = module.params.get('tag_value') public_ipv4_pool = module.params.get('public_ipv4_pool') + tags = module.params.get('tags') + purge_tags = module.params.get('purge_tags') if instance_id: is_instance = True @@ -575,6 +590,7 @@ def main(): module.fail_json(msg="If you are specifying an ENI, in_vpc must be true") is_instance = False + # Tags for *searching* for an EIP. tag_dict = generate_tag_dict(module, tag_name, tag_value) try: @@ -603,6 +619,10 @@ def main(): 'public_ip': address['PublicIp'], 'allocation_id': address['AllocationId'] } + + result['changed'] |= ensure_ec2_tags( + ec2, module, result['allocation_id'], + resource_type='elastic-ip', tags=tags, purge_tags=purge_tags) else: if device_id: disassociated = ensure_absent( diff --git a/plugins/modules/ec2_eip_info.py b/plugins/modules/ec2_eip_info.py index 553930db67a..e38735c087e 100644 --- a/plugins/modules/ec2_eip_info.py +++ b/plugins/modules/ec2_eip_info.py @@ -97,22 +97,25 @@ ''' -from ansible_collections.amazon.aws.plugins.module_utils.core import AnsibleAWSModule -from ansible_collections.amazon.aws.plugins.module_utils.ec2 import (ansible_dict_to_boto3_filter_list, - boto3_tag_list_to_ansible_dict, - camel_dict_to_snake_dict, - ) try: from botocore.exceptions import (BotoCoreError, ClientError) except ImportError: pass # caught by imported AnsibleAWSModule +from ansible.module_utils.common.dict_transformations import camel_dict_to_snake_dict + +from ansible_collections.amazon.aws.plugins.module_utils.core import AnsibleAWSModule +from ansible_collections.amazon.aws.plugins.module_utils.ec2 import AWSRetry +from ansible_collections.amazon.aws.plugins.module_utils.ec2 import ansible_dict_to_boto3_filter_list +from ansible_collections.amazon.aws.plugins.module_utils.ec2 import boto3_tag_list_to_ansible_dict + def get_eips_details(module): - connection = module.client('ec2') + connection = module.client('ec2', retry_decorator=AWSRetry.jittered_backoff()) filters = module.params.get("filters") try: response = connection.describe_addresses( + aws_retry=True, Filters=ansible_dict_to_boto3_filter_list(filters) ) except (BotoCoreError, ClientError) as e: diff --git a/tests/integration/targets/ec2_eip/defaults/main.yml b/tests/integration/targets/ec2_eip/defaults/main.yml index bbaeb04820c..03b1ba51de0 100644 --- a/tests/integration/targets/ec2_eip/defaults/main.yml +++ b/tests/integration/targets/ec2_eip/defaults/main.yml @@ -3,3 +3,4 @@ # run multiple copies of the test concurrently. vpc_cidr: '10.{{ 256 | random(seed=resource_prefix) }}.0.0/16' subnet_cidr: '10.{{ 256 | random(seed=resource_prefix) }}.42.0/24' +subnet_az: '{{ ec2_availability_zone_names[0] }}' diff --git a/tests/integration/targets/ec2_eip/meta/main.yml b/tests/integration/targets/ec2_eip/meta/main.yml index 1f64f1169a9..930e8622824 100644 --- a/tests/integration/targets/ec2_eip/meta/main.yml +++ b/tests/integration/targets/ec2_eip/meta/main.yml @@ -1,3 +1,3 @@ dependencies: - prepare_tests - - setup_ec2 + - setup_ec2_facts diff --git a/tests/integration/targets/ec2_eip/tasks/main.yml b/tests/integration/targets/ec2_eip/tasks/main.yml index 9f03f5b5647..48db1d1048a 100644 --- a/tests/integration/targets/ec2_eip/tasks/main.yml +++ b/tests/integration/targets/ec2_eip/tasks/main.yml @@ -17,9 +17,6 @@ - name: list available AZs aws_az_info: null register: region_azs - - name: pick an AZ for testing - set_fact: - subnet_az: '{{ region_azs.availability_zones[0].zone_name }}' - name: create a VPC ec2_vpc_net: name: '{{ resource_prefix }}-vpc' @@ -40,12 +37,6 @@ state: present vpc_id: '{{ vpc_result.vpc.id }}' register: vpc_igw - - name: "Find AMI to use" - ec2_ami_info: - owners: 'amazon' - filters: - name: 'amzn2-ami-hvm-2.0.20190612-x86_64-gp2' - register: ec2_amis - name: "create a security group" ec2_group: state: present @@ -61,10 +52,11 @@ - name: Create instance for attaching ec2_instance: name: '{{ resource_prefix }}-instance' - image_id: '{{ ec2_amis.images[0].image_id }}' + image_id: '{{ ec2_ami_id }}' security_group: '{{ security_group.group_id }}' vpc_subnet_id: '{{ vpc_subnet_create.subnet.id }}' - wait: no ## Don't delay the tests, we'll check again before we need it + wait: yes + state: running register: create_ec2_instance_result # ===================================================== @@ -91,6 +83,7 @@ tags: AnsibleEIPTest: Running AnsibleEIPTestPrefix: '{{ resource_prefix }}' + # ===================================================== - name: Get current state of EIPs ec2_eip_info: null @@ -101,10 +94,14 @@ - eip_info_start is defined - '"addresses" in eip_info_start' - ( eip_info_start.addresses | length ) == ( eip_info_start | community.general.json_query("addresses[].association_id") | length ) + - name: Allocate a new eip (no conditions) ec2_eip: state: present + tags: + AnsibleEIPTestPrefix: '{{ resource_prefix }}' register: eip + - ec2_eip_info: null register: eip_info - assert: @@ -114,6 +111,7 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - ec2_eip_info: filters: public-ip: '{{ eip.public_ip }}' @@ -124,6 +122,9 @@ - eip_info.addresses[0].allocation_id == eip.allocation_id - eip_info.addresses[0].domain == "vpc" - eip_info.addresses[0].public_ip == eip.public_ip + - '"AnsibleEIPTestPrefix" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['AnsibleEIPTestPrefix'] == resource_prefix + - ec2_eip_info: filters: allocation-id: '{{ eip.allocation_id }}' @@ -134,6 +135,7 @@ - eip_info.addresses[0].allocation_id == eip.allocation_id - eip_info.addresses[0].domain == "vpc" - eip_info.addresses[0].public_ip == eip.public_ip + - name: Release eip ec2_eip: state: absent @@ -146,6 +148,7 @@ - eip_release is defined - eip_release is changed - ( eip_info_start.addresses | length ) == ( eip_info.addresses | length ) + - name: Allocate a new eip - attempt reusing unallocated ones (none available) ec2_eip: state: present @@ -160,6 +163,7 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: Re-Allocate a new eip - attempt reusing unallocated ones (one available) ec2_eip: state: present @@ -174,6 +178,7 @@ - reallocate_eip.public_ip is defined and ( reallocate_eip.public_ip | ansible.netcommon.ipaddr ) - reallocate_eip.allocation_id is defined and reallocate_eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: Release eip ec2_eip: state: absent @@ -186,6 +191,7 @@ - ( eip_info_start.addresses | length ) == ( eip_info.addresses | length ) - eip_release is defined - eip_release is changed + - name: Allocate a new eip ec2_eip: state: present @@ -199,6 +205,7 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: Match an existing eip (changed == false) ec2_eip: state: present @@ -213,6 +220,7 @@ - reallocate_eip.public_ip is defined and ( reallocate_eip.public_ip | ansible.netcommon.ipaddr ) - reallocate_eip.allocation_id is defined and reallocate_eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: Release eip ec2_eip: state: absent @@ -225,6 +233,7 @@ - eip_release is defined - eip_release is changed - ( eip_info_start.addresses | length ) == ( eip_info.addresses | length ) + - name: Allocate a new eip (no tags) ec2_eip: state: present @@ -238,6 +247,7 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: attempt reusing an existing eip with a tag (No match available) ec2_eip: state: present @@ -253,12 +263,14 @@ - no_tagged_eip.public_ip is defined and ( no_tagged_eip.public_ip | ansible.netcommon.ipaddr ) - no_tagged_eip.allocation_id is defined and no_tagged_eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 2 == ( eip_info.addresses | length ) + - name: tag eip so we can try matching it - ec2_tag: + ec2_eip: state: present - resource: '{{ eip.allocation_id }}' + public_ip: '{{ eip.public_ip }}' tags: Team: Frontend + - name: attempt reusing an existing eip with a tag (Match available) ec2_eip: state: present @@ -274,6 +286,7 @@ - reallocate_eip.public_ip is defined and ( reallocate_eip.public_ip | ansible.netcommon.ipaddr ) - reallocate_eip.allocation_id is defined and reallocate_eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 2 == ( eip_info.addresses | length ) + - name: attempt reusing an existing eip with a tag and it's value (no match available) ec2_eip: state: present @@ -290,12 +303,14 @@ - backend_eip.public_ip is defined and ( backend_eip.public_ip | ansible.netcommon.ipaddr ) - backend_eip.allocation_id is defined and backend_eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 3 == ( eip_info.addresses | length ) + - name: tag eip so we can try matching it - ec2_tag: + ec2_eip: state: present - resource: '{{ eip.allocation_id }}' + public_ip: '{{ eip.public_ip }}' tags: Team: Backend + - name: attempt reusing an existing eip with a tag and it's value (match available) ec2_eip: state: present @@ -312,6 +327,7 @@ - reallocate_eip.public_ip is defined and reallocate_eip.public_ip != "" - reallocate_eip.allocation_id is defined and reallocate_eip.allocation_id != "" - ( eip_info_start.addresses | length ) + 3 == ( eip_info.addresses | length ) + - name: Release backend_eip ec2_eip: state: absent @@ -324,6 +340,7 @@ - eip_release is defined - eip_release is changed - ( eip_info_start.addresses | length ) + 2 == ( eip_info.addresses | length ) + - name: Release no_tagged_eip ec2_eip: state: absent @@ -336,6 +353,7 @@ - eip_release is defined - eip_release is changed - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: Release eip ec2_eip: state: absent @@ -348,6 +366,7 @@ - eip_release is defined - eip_release is changed - ( eip_info_start.addresses | length ) == ( eip_info.addresses | length ) + - name: allocate a new eip from a pool ec2_eip: state: present @@ -362,14 +381,17 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + - name: create ENI A ec2_eni: subnet_id: '{{ vpc_subnet_create.subnet.id }}' register: eni_create_a + - name: create ENI B ec2_eni: subnet_id: '{{ vpc_subnet_create.subnet.id }}' register: eni_create_b + - name: Attach EIP to ENI A ec2_eip: public_ip: '{{ eip.public_ip }}' @@ -393,6 +415,7 @@ - eip_info.addresses[0].network_interface_id == eni_create_a.interface.id - eip_info.addresses[0].private_ip_address is defined and ( eip_info.addresses[0].private_ip_address | ansible.netcommon.ipaddr ) - eip_info.addresses[0].network_interface_owner_id == caller_info.account + - name: Re-Attach EIP to ENI A (no change) ec2_eip: public_ip: '{{ eip.public_ip }}' @@ -415,6 +438,7 @@ - eip_info.addresses[0].association_id is defined and eip_info.addresses[0].association_id.startswith("eipassoc-") - eip_info.addresses[0].network_interface_id == eni_create_a.interface.id - eip_info.addresses[0].private_ip_address is defined and ( eip_info.addresses[0].private_ip_address | ansible.netcommon.ipaddr ) + - name: Attach EIP to ENI B (should fail, already associated) ec2_eip: public_ip: '{{ eip.public_ip }}' @@ -436,6 +460,7 @@ - eip_info.addresses[0].association_id is defined and eip_info.addresses[0].association_id.startswith("eipassoc-") - eip_info.addresses[0].network_interface_id == eni_create_a.interface.id - eip_info.addresses[0].private_ip_address is defined and ( eip_info.addresses[0].private_ip_address | ansible.netcommon.ipaddr ) + - name: Attach EIP to ENI B ec2_eip: public_ip: '{{ eip.public_ip }}' @@ -459,6 +484,7 @@ - eip_info.addresses[0].association_id is defined and eip_info.addresses[0].association_id.startswith("eipassoc-") - eip_info.addresses[0].network_interface_id == eni_create_b.interface.id - eip_info.addresses[0].private_ip_address is defined and ( eip_info.addresses[0].private_ip_address | ansible.netcommon.ipaddr ) + - name: Detach EIP from ENI B, without enabling release on disassociation ec2_eip: state: absent @@ -474,6 +500,7 @@ - associate_eip is defined - associate_eip is changed - eip_info.addresses | length == 1 + - name: Re-detach EIP from ENI B, without enabling release on disassociation ec2_eip: state: absent @@ -489,6 +516,7 @@ - associate_eip is defined - associate_eip is not changed - eip_info.addresses | length == 1 + - name: Attach EIP to ENI A ec2_eip: public_ip: '{{ eip.public_ip }}' @@ -505,6 +533,7 @@ - associate_eip.public_ip is defined and eip.public_ip == associate_eip.public_ip - associate_eip.allocation_id is defined and eip.allocation_id == associate_eip.allocation_id - eip_info.addresses[0].network_interface_id == eni_create_a.interface.id + - name: Detach EIP from ENI A, enabling release on disassociation ec2_eip: state: absent @@ -521,6 +550,7 @@ - associate_eip is defined - associate_eip is changed - eip_info.addresses | length == 0 + - name: Re-detach EIP from ENI A, enabling release on disassociation ec2_eip: state: absent @@ -537,28 +567,26 @@ - associate_eip is defined - associate_eip is not changed - eip_info.addresses | length == 0 + - ec2_eip_info: null register: eip_info - assert: that: - ( eip_info_start.addresses | length ) == ( eip_info.addresses | length ) + - name: Cleanup ENI B ec2_eni: state: absent eni_id: '{{ eni_create_b.interface.id }}' + - name: Cleanup ENI A ec2_eni: state: absent eni_id: '{{ eni_create_a.interface.id }}' - - name: Make sure the instance is ready - ec2_instance_info: - filters: - "tag:Name": '{{ resource_prefix }}-instance' - register: instance_info - until: instance_info.instances[0].state.name == 'running' + - name: Attach eip to an EC2 instance ec2_eip: - device_id: '{{ instance_info.instances[0].instance_id }}' + device_id: '{{ create_ec2_instance_result.instance_ids[0] }}' state: present release_on_disassociation: yes register: instance_eip @@ -570,11 +598,12 @@ that: - instance_eip is success - eip_info.addresses[0].allocation_id is defined - - eip_info.addresses[0].instance_id == '{{ instance_info.instances[0].instance_id }}' + - eip_info.addresses[0].instance_id == '{{ create_ec2_instance_result.instance_ids[0] }}' + - name: Attach eip to an EC2 instance with private Ip specified ec2_eip: - device_id: '{{ instance_info.instances[0].instance_id }}' - private_ip_address: '{{ instance_info.instances[0].private_ip_address }}' + device_id: '{{ create_ec2_instance_result.instance_ids[0] }}' + private_ip_address: '{{ create_ec2_instance_result.instances[0].private_ip_address }}' state: present release_on_disassociation: yes register: instance_eip @@ -586,12 +615,15 @@ that: - instance_eip is success - eip_info.addresses[0].allocation_id is defined - - eip_info.addresses[0].instance_id == '{{ instance_info.instances[0].instance_id }}' + - eip_info.addresses[0].instance_id == '{{ create_ec2_instance_result.instance_ids[0] }}' + # ===================================================== + - name: Cleanup instance ec2_instance: instance_ids: '{{ create_ec2_instance_result.instance_ids }}' state: absent + - name: Cleanup instance eip ec2_eip: state: absent @@ -600,26 +632,31 @@ retries: 5 delay: 5 until: eip_cleanup is successful + - name: Cleanup IGW ec2_vpc_igw: state: absent vpc_id: '{{ vpc_result.vpc.id }}' register: vpc_igw + - name: Cleanup security group ec2_group: state: absent name: '{{ resource_prefix }}-sg' + - name: Cleanup Subnet ec2_vpc_subnet: state: absent cidr: '{{ subnet_cidr }}' vpc_id: '{{ vpc_result.vpc.id }}' + - name: Release eip ec2_eip: state: absent public_ip: '{{ eip.public_ip }}' register: eip_release ignore_errors: true + - name: allocate a new eip ec2_eip: state: present @@ -633,6 +670,129 @@ - eip.public_ip is defined and ( eip.public_ip | ansible.netcommon.ipaddr ) - eip.allocation_id is defined and eip.allocation_id.startswith("eipalloc-") - ( eip_info_start.addresses | length ) + 1 == ( eip_info.addresses | length ) + + ############################################################################################# + + - name: Tag EIP + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + AnsibleEIPTestPrefix: '{{ resource_prefix }}' + another_tag: 'another Value {{ resource_prefix }}' + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is changed + - '"AnsibleEIPTestPrefix" in eip_info.addresses[0].tags' + - '"another_tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['AnsibleEIPTestPrefix'] == resource_prefix + - eip_info.addresses[0].tags['another_tag'] == 'another Value ' + resource_prefix + + - name: Tag EIP + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + AnsibleEIPTestPrefix: '{{ resource_prefix }}' + another_tag: 'another Value {{ resource_prefix }}' + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is not changed + - '"AnsibleEIPTestPrefix" in eip_info.addresses[0].tags' + - '"another_tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['AnsibleEIPTestPrefix'] == resource_prefix + - eip_info.addresses[0].tags['another_tag'] == 'another Value ' + resource_prefix + + - name: Add another Tag + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + "third tag": 'Third tag - {{ resource_prefix }}' + purge_tags: False + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is changed + - '"AnsibleEIPTestPrefix" in eip_info.addresses[0].tags' + - '"another_tag" in eip_info.addresses[0].tags' + - '"third tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['AnsibleEIPTestPrefix'] == resource_prefix + - eip_info.addresses[0].tags['another_tag'] == 'another Value ' + resource_prefix + - eip_info.addresses[0].tags['third tag'] == 'Third tag - ' + resource_prefix + + - name: Add another Tag + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + "third tag": 'Third tag - {{ resource_prefix }}' + purge_tags: False + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is not changed + - '"AnsibleEIPTestPrefix" in eip_info.addresses[0].tags' + - '"another_tag" in eip_info.addresses[0].tags' + - '"third tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['AnsibleEIPTestPrefix'] == resource_prefix + - eip_info.addresses[0].tags['another_tag'] == 'another Value ' + resource_prefix + - eip_info.addresses[0].tags['third tag'] == 'Third tag - ' + resource_prefix + + - name: Purge most tags + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + "third tag": 'Third tag - {{ resource_prefix }}' + purge_tags: True + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is changed + - '"AnsibleEIPTestPrefix" not in eip_info.addresses[0].tags' + - '"another_tag" not in eip_info.addresses[0].tags' + - '"third tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['third tag'] == 'Third tag - ' + resource_prefix + + - name: Purge most tags + ec2_eip: + state: present + public_ip: '{{ eip.public_ip }}' + tags: + "third tag": 'Third tag - {{ resource_prefix }}' + purge_tags: True + register: tag_eip + - ec2_eip_info: null + register: eip_info + - assert: + that: + - tag_eip is defined + - tag_eip is not changed + - '"AnsibleEIPTestPrefix" not in eip_info.addresses[0].tags' + - '"another_tag" not in eip_info.addresses[0].tags' + - '"third tag" in eip_info.addresses[0].tags' + - eip_info.addresses[0].tags['third tag'] == 'Third tag - ' + resource_prefix + + ############################################################################################# + - name: Release eip ec2_eip: state: absent