Repository: getmoto/moto

Issue:
Add support for tag filters to DescribeNetworkInterfaces in mock_ec2
Hi,

Get the following when running a test I've setup: 

``` python
NotImplementedError: The filter 'tag:component' for DescribeNetworkInterfaces has not been implemented in Moto yet.
```

Happy to submit a PR for this if you could give me a few pointers as to where this needs to be added.



Discussion:
It looks like we will need another conditional [here](https://github.com/spulec/moto/blob/master/moto/ec2/models.py#L239). A PR would happily be accepted.


Resolving patch:
diff --git a/moto/ec2/models.py b/moto/ec2/models.py
--- a/moto/ec2/models.py
+++ b/moto/ec2/models.py
@@ -404,6 +404,7 @@ def create_network_interface(
         private_ip_addresses=None,
         group_ids=None,
         description=None,
+        tags=None,
         **kwargs
     ):
         eni = NetworkInterface(
@@ -415,6 +416,8 @@ def create_network_interface(
             description=description,
             **kwargs
         )
+        if tags:
+            eni.add_tags(tags)
         self.enis[eni.id] = eni
         return eni
 
diff --git a/moto/ec2/responses/elastic_network_interfaces.py b/moto/ec2/responses/elastic_network_interfaces.py
--- a/moto/ec2/responses/elastic_network_interfaces.py
+++ b/moto/ec2/responses/elastic_network_interfaces.py
@@ -11,9 +11,17 @@ def create_network_interface(self):
         groups = self._get_multi_param("SecurityGroupId")
         subnet = self.ec2_backend.get_subnet(subnet_id)
         description = self._get_param("Description")
+        tags = self._parse_tag_specification("TagSpecification").get(
+            "network-interface"
+        )
         if self.is_not_dryrun("CreateNetworkInterface"):
             eni = self.ec2_backend.create_network_interface(
-                subnet, private_ip_address, private_ip_addresses, groups, description
+                subnet,
+                private_ip_address,
+                private_ip_addresses,
+                groups,
+                description,
+                tags,
             )
             template = self.response_template(CREATE_NETWORK_INTERFACE_RESPONSE)
             return template.render(eni=eni)


Test patch:
diff --git a/tests/test_ec2/test_elastic_network_interfaces.py b/tests/test_ec2/test_elastic_network_interfaces.py
--- a/tests/test_ec2/test_elastic_network_interfaces.py
+++ b/tests/test_ec2/test_elastic_network_interfaces.py
@@ -499,3 +499,64 @@ def test_elastic_network_interfaces_describe_network_interfaces_with_filter():
         eni1.private_ip_address
     )
     response["NetworkInterfaces"][0]["Description"].should.equal(eni1.description)
+
+
+@mock_ec2
+def test_elastic_network_interfaces_filter_by_tag():
+    ec2 = boto3.resource("ec2", region_name="us-west-2")
+    ec2_client = boto3.client("ec2", region_name="us-west-2")
+
+    vpc = ec2.create_vpc(CidrBlock="10.0.0.0/16")
+    subnet = ec2.create_subnet(
+        VpcId=vpc.id, CidrBlock="10.0.0.0/24", AvailabilityZone="us-west-2a"
+    )
+
+    eni_dev = ec2.create_network_interface(
+        SubnetId=subnet.id,
+        PrivateIpAddress="10.0.10.5",
+        Description="dev interface",
+        TagSpecifications=[
+            {
+                "ResourceType": "network-interface",
+                "Tags": [{"Key": "environment", "Value": "dev"}],
+            },
+        ],
+    )
+
+    eni_prod = ec2.create_network_interface(
+        SubnetId=subnet.id,
+        PrivateIpAddress="10.0.10.6",
+        Description="prod interface",
+        TagSpecifications=[
+            {
+                "ResourceType": "network-interface",
+                "Tags": [{"Key": "environment", "Value": "prod"}],
+            },
+        ],
+    )
+
+    for eni in [eni_dev, eni_prod]:
+        waiter = ec2_client.get_waiter("network_interface_available")
+        waiter.wait(NetworkInterfaceIds=[eni.id])
+
+    resp = ec2_client.describe_network_interfaces(
+        Filters=[{"Name": "tag:environment", "Values": ["staging"]}]
+    )
+    resp["NetworkInterfaces"].should.have.length_of(0)
+
+    resp = ec2_client.describe_network_interfaces(
+        Filters=[{"Name": "tag:environment", "Values": ["dev"]}]
+    )
+    resp["NetworkInterfaces"].should.have.length_of(1)
+    resp["NetworkInterfaces"][0]["Description"].should.equal("dev interface")
+
+    resp = ec2_client.describe_network_interfaces(
+        Filters=[{"Name": "tag:environment", "Values": ["prod"]}]
+    )
+    resp["NetworkInterfaces"].should.have.length_of(1)
+    resp["NetworkInterfaces"][0]["Description"].should.equal("prod interface")
+
+    resp = ec2_client.describe_network_interfaces(
+        Filters=[{"Name": "tag:environment", "Values": ["dev", "prod"]}]
+    )
+    resp["NetworkInterfaces"].should.have.length_of(2)