Repository: cloud-custodian/cloud-custodian

Issue:
Metrics are not applied for Network load balancers when used in filter
**Describe the bug**
Working on a filter criteria by applying the metrics 'ActiveFlowCount' with stats 'Sum' did not give any result.There was no result even with other metrics and statisic combinations.

**To Reproduce**
1. Create a network load Balancers such that it is under utilized.
2. Run the c7n policy provided below
https://gitter.im/cloud-custodian/cloud-custodian?at=5e94c9f1d021c45cc7e33280
**Expected behavior**
A clear and concise description of what you expected to happen.
A list of NLB must be filtered based on the set filter criteria.
https://gitter.im/cloud-custodian/cloud-custodian?at=5e94c9f1d021c45cc7e33280

**Background (please complete the following information):**
 - OS: amazon 2018.03
 - Python Version: Python 2.7.16
 - Custodian Version: 0.8.46.1
 - Cloud Provider: aws

```yaml
policies: 
resource: app-elb
filters:
 - type: value                                                              
   key: LoadBalancerArn                                                     
   op: contains                                                             
   value: loadbalancer/net                                                  
 - type: metrics                                                            
   name: ActiveFlowCount                                                    
   statistics: Sum                                                          
   days: 14                                                                 
   value: 100
   op: less-than
```
https://gitter.im/cloud-custodian/cloud-custodian?at=5e94c9f1d021c45cc7e33280


Discussion:

Resolving patch:
diff --git a/c7n/resources/appelb.py b/c7n/resources/appelb.py
--- a/c7n/resources/appelb.py
+++ b/c7n/resources/appelb.py
@@ -12,7 +12,7 @@
 # See the License for the specific language governing permissions and
 # limitations under the License.
 """
-Application Load Balancers
+Application & Network Load Balancers
 """
 import json
 import logging
@@ -31,6 +31,7 @@
 from c7n.utils import (
     local_session, chunks, type_schema, get_retry, set_annotation)
 
+from c7n.resources.aws import Arn
 from c7n.resources.shield import IsShieldProtected, SetShieldProtection
 
 log = logging.getLogger('custodian.app-elb')
@@ -144,21 +145,44 @@ def _process_tags(alb_set):
 
 @AppELB.filter_registry.register('metrics')
 class AppElbMetrics(MetricsFilter):
-    """Filter app load balancer by metric values.
+    """Filter app/net load balancer by metric values.
 
-    See available metrics here
+    Note application and network load balancers use different Cloud
+    Watch metrics namespaces and metric names, the custodian app-elb
+    resource returns both types of load balancer, so an additional
+    filter should be used to ensure only targeting a particular
+    type. ie.  `- Type: application` or `- Type: network`
+
+    See available application load balancer metrics here
     https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-cloudwatch-metrics.html
 
-    Custodian defaults to specifying dimensions for the app elb only.
-    Target Group dimension not supported atm.
+    See available network load balancer metrics here.
+    https://docs.aws.amazon.com/elasticloadbalancing/latest/network/load-balancer-cloudwatch-metrics.html
+
+
+    For network load balancer metrics, the metrics filter requires specifying
+    the namespace parameter to the filter.
+
+    .. code-block:: yaml
+
+      policies:
+        - name: net-lb-underutilized
+          resource: app-elb
+          filters:
+           - Type: network
+           - type: metrics
+             name: ActiveFlowCount
+             namespace: AWS/NetworkELB
+             statistics: Sum
+             days: 14
+             value: 100
+             op: less-than
     """
 
     def get_dimensions(self, resource):
         return [{
             'Name': self.model.dimension,
-            'Value': 'app/%s/%s' % (
-                resource[self.model.name],
-                resource[self.model.id].rsplit('/')[-1])}]
+            'Value': Arn.parse(resource['LoadBalancerArn']).resource}]
 
 
 @AppELB.filter_registry.register('security-group')


Test patch:
diff --git a/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeLoadBalancers_1.json b/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeLoadBalancers_1.json
new file mode 100644
--- /dev/null
+++ b/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeLoadBalancers_1.json
@@ -0,0 +1,34 @@
+{
+    "status_code": 200,
+    "data": {
+        "LoadBalancers": [
+            {
+                "LoadBalancerArn": "arn:aws:elasticloadbalancing:us-east-1:644160558196:loadbalancer/net/nicnoc/d1c62a508f72274f",
+                "DNSName": "nicnoc-d1c62a508f72274f.elb.us-east-1.amazonaws.com",
+                "CanonicalHostedZoneId": "Z26RNL4JYFTOTI",
+                "CreatedTime": "2020-04-18T11:01:21.041000+00:00",
+                "LoadBalancerName": "nicnoc",
+                "Scheme": "internet-facing",
+                "VpcId": "vpc-d2d616b5",
+                "State": {
+                    "Code": "active"
+                },
+                "Type": "network",
+                "AvailabilityZones": [
+                    {
+                        "ZoneName": "us-east-1b",
+                        "SubnetId": "subnet-efbcccb7",
+                        "LoadBalancerAddresses": []
+                    },
+                    {
+                        "ZoneName": "us-east-1a",
+                        "SubnetId": "subnet-914763e7",
+                        "LoadBalancerAddresses": []
+                    }
+                ],
+                "IpAddressType": "ipv4"
+            }
+        ],
+        "ResponseMetadata": {}
+    }
+}
diff --git a/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeTags_1.json b/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeTags_1.json
new file mode 100644
--- /dev/null
+++ b/tests/data/placebo/test_netelb_metrics/elasticloadbalancing.DescribeTags_1.json
@@ -0,0 +1,17 @@
+{
+    "status_code": 200,
+    "data": {
+        "TagDescriptions": [
+            {
+                "ResourceArn": "arn:aws:elasticloadbalancing:us-east-1:644160558196:loadbalancer/net/nicnoc/d1c62a508f72274f",
+                "Tags": [
+                    {
+                        "Key": "Env",
+                        "Value": "Dev"
+                    }
+                ]
+            }
+        ],
+        "ResponseMetadata": {}
+    }
+}
diff --git a/tests/data/placebo/test_netelb_metrics/monitoring.GetMetricStatistics_1.json b/tests/data/placebo/test_netelb_metrics/monitoring.GetMetricStatistics_1.json
new file mode 100644
--- /dev/null
+++ b/tests/data/placebo/test_netelb_metrics/monitoring.GetMetricStatistics_1.json
@@ -0,0 +1,14 @@
+{
+    "status_code": 200,
+    "data": {
+        "Label": "TCP_ELB_Reset_Count",
+        "Datapoints": [
+            {
+                "Timestamp": "2020-04-18T07:10:00+00:00",
+                "Sum": 37.0,
+                "Unit": "Count"
+            }
+        ],
+        "ResponseMetadata": {}
+    }
+}
\ No newline at end of file
diff --git a/tests/test_appelb.py b/tests/test_appelb.py
--- a/tests/test_appelb.py
+++ b/tests/test_appelb.py
@@ -421,6 +421,28 @@ def test_appelb_waf(self):
             resources[0]["LoadBalancerArn"], post_resources[0]["LoadBalancerArn"]
         )
 
+    def test_appelb_net_metrics(self):
+        factory = self.replay_flight_data('test_netelb_metrics')
+        p = self.load_policy({
+            'name': 'netelb-metrics',
+            'resource': 'app-elb',
+            'filters': [
+                {'Type': 'network'},
+                {'type': 'metrics',
+                 'name': 'TCP_ELB_Reset_Count',
+                 'namespace': 'AWS/NetworkELB',
+                 'statistics': 'Sum',
+                 'value': 10,
+                 'op': 'greater-than',
+                 'days': 0.25}]},
+            session_factory=factory)
+        resources = p.run()
+        self.assertEqual(len(resources), 1)
+        self.assertEqual(resources[0]['LoadBalancerName'], 'nicnoc')
+        self.assertTrue(
+            'AWS/NetworkELB.TCP_ELB_Reset_Count.Sum' in resources[
+                0]['c7n.metrics'])
+
 
 class AppELBHealthcheckProtocolMismatchTest(BaseTest):