From a4701dbbe692826ab1cd75a1d54fc4fe7f19f9ae Mon Sep 17 00:00:00 2001 From: Wolfgang Bauer Date: Fri, 25 Sep 2020 16:25:30 +0200 Subject: [PATCH] Add tags to Elastic IP Addresses (#3310) * Make ElasticAddress a tagged resource To be able to filter on tags on ElasticAddresses, I need to have tags. * remove unneeded commented lines Was beginning of how to to it before further checking how it is done with other resources. * do not ignore network-interface-owner-id filter * add TODO about currently hardcoded region * remove hardcoding region * add testing for tags creating and allocation, adding tags and querying for it * separate test for tags into own method * Linting Co-authored-by: Bert Blommers --- moto/ec2/models.py | 16 +++++--- tests/test_ec2/test_elastic_ip_addresses.py | 45 +++++++++++++++++++++ 2 files changed, 56 insertions(+), 5 deletions(-) diff --git a/moto/ec2/models.py b/moto/ec2/models.py index 60f17912..5e55b627 100644 --- a/moto/ec2/models.py +++ b/moto/ec2/models.py @@ -4510,13 +4510,15 @@ class SpotFleetBackend(object): return True -class ElasticAddress(CloudFormationModel): - def __init__(self, domain, address=None): +class ElasticAddress(TaggedEC2Resource, CloudFormationModel): + def __init__(self, ec2_backend, domain, address=None): + self.ec2_backend = ec2_backend if address: self.public_ip = address else: self.public_ip = random_ip() self.allocation_id = random_eip_allocation_id() if domain == "vpc" else None + self.id = self.allocation_id self.domain = domain self.instance = None self.eni = None @@ -4578,9 +4580,13 @@ class ElasticAddress(CloudFormationModel): return self.eni.private_ip_address elif filter_name == "public-ip": return self.public_ip - else: + elif filter_name == "network-interface-owner-id": # TODO: implement network-interface-owner-id raise FilterNotImplementedError(filter_name, "DescribeAddresses") + else: + return super(ElasticAddress, self).get_filter_value( + filter_name, "DescribeAddresses" + ) class ElasticAddressBackend(object): @@ -4592,9 +4598,9 @@ class ElasticAddressBackend(object): if domain not in ["standard", "vpc"]: raise InvalidDomainError(domain) if address: - address = ElasticAddress(domain, address) + address = ElasticAddress(self, domain=domain, address=address) else: - address = ElasticAddress(domain) + address = ElasticAddress(self, domain=domain) self.addresses.append(address) return address diff --git a/tests/test_ec2/test_elastic_ip_addresses.py b/tests/test_ec2/test_elastic_ip_addresses.py index 886cdff5..baecb94d 100644 --- a/tests/test_ec2/test_elastic_ip_addresses.py +++ b/tests/test_ec2/test_elastic_ip_addresses.py @@ -537,3 +537,48 @@ def test_eip_filters(): service.vpc_addresses.filter(Filters=[{"Name": "domain", "Values": ["vpc"]}]) ) len(addresses).should.equal(3) + + +@mock_ec2 +def test_eip_tags(): + service = boto3.resource("ec2", region_name="us-west-1") + client = boto3.client("ec2", region_name="us-west-1") + + # Allocate one address without tags + client.allocate_address(Domain="vpc") + # Allocate one address and add tags + alloc_tags = client.allocate_address(Domain="vpc") + with_tags = client.create_tags( + Resources=[alloc_tags["AllocationId"]], + Tags=[{"Key": "ManagedBy", "Value": "MyCode"}], + ) + addresses_with_tags = client.describe_addresses( + Filters=[ + {"Name": "domain", "Values": ["vpc"]}, + {"Name": "tag:ManagedBy", "Values": ["MyCode"]}, + ] + ) + len(addresses_with_tags["Addresses"]).should.equal(1) + addresses_with_tags = list( + service.vpc_addresses.filter( + Filters=[ + {"Name": "domain", "Values": ["vpc"]}, + {"Name": "tag:ManagedBy", "Values": ["MyCode"]}, + ] + ) + ) + len(addresses_with_tags).should.equal(1) + addresses_with_tags = list( + service.vpc_addresses.filter( + Filters=[ + {"Name": "domain", "Values": ["vpc"]}, + {"Name": "tag:ManagedBy", "Values": ["SomethingOther"]}, + ] + ) + ) + len(addresses_with_tags).should.equal(0) + addresses = list( + service.vpc_addresses.filter(Filters=[{"Name": "domain", "Values": ["vpc"]}]) + ) + # Expected total is 2, one with and one without tags + len(addresses).should.equal(2)