diff --git a/sdk/monitor/azure-monitor-query/CHANGELOG.md b/sdk/monitor/azure-monitor-query/CHANGELOG.md index cb3fe811522d..0969530e1cbe 100644 --- a/sdk/monitor/azure-monitor-query/CHANGELOG.md +++ b/sdk/monitor/azure-monitor-query/CHANGELOG.md @@ -8,6 +8,7 @@ - Added `status` attribute to `LogsQueryResult`. - Added `LogsQueryStatus` Enum to describe the status of a result. - Added a new `LogsTableRow` type that represents a single row in a table. +- Items in `metrics` list in `MetricsResult` can now be accessed by metric names. ### Breaking Changes diff --git a/sdk/monitor/azure-monitor-query/azure/monitor/query/_models.py b/sdk/monitor/azure-monitor-query/azure/monitor/query/_models.py index 18c1bd3ae510..8aa3cdd867bf 100644 --- a/sdk/monitor/azure-monitor-query/azure/monitor/query/_models.py +++ b/sdk/monitor/azure-monitor-query/azure/monitor/query/_models.py @@ -57,7 +57,7 @@ def _from_generated(cls, generated): ) -class LogsTableRow(object): +class LogsTableRow(list): """Represents a single row in logs table. :ivar int index: The index of the row in the table @@ -65,6 +65,7 @@ class LogsTableRow(object): def __init__(self, **kwargs): # type: (Any) -> None + super(LogsTableRow, self).__init__(**kwargs) _col_types = kwargs["col_types"] row = kwargs["row"] self._row = process_row(_col_types, row) @@ -76,6 +77,12 @@ def __iter__(self): """This will iterate over the row directly.""" return iter(self._row) + def __len__(self): + return len(self._row) + + def __repr__(self): + return repr(self._row) + def __getitem__(self, column): """This type must be subscriptable directly to row. Must be gettableby both column name and row index @@ -131,11 +138,34 @@ def _from_generated(cls, generated): granularity=generated.interval, namespace=generated.namespace, resource_region=generated.resourceregion, - metrics=[ + metrics=MetricsList(metrics=[ Metric._from_generated(m) for m in generated.value # pylint: disable=protected-access - ], + ]), ) +class MetricsList(list): + """Custom list for metrics + """ + def __init__(self, **kwargs): + super(MetricsList, self).__init__(**kwargs) + self._metrics = kwargs['metrics'] + self._metric_names = {val.name: ind for ind, val in enumerate(self._metrics)} + + def __iter__(self): + return iter(self._metrics) + + def __len__(self): + return len(self._metrics) + + def __repr__(self): + return repr(self._metrics) + + def __getitem__(self, metric): + try: + return self._metrics[metric] + except TypeError: # TypeError: list indices must be integers or slices, not str + return self._metrics[self._metric_names[metric]] + class LogsBatchQuery(object): """A single request in a batch. diff --git a/sdk/monitor/azure-monitor-query/tests/async/test_metrics_client_async.py b/sdk/monitor/azure-monitor-query/tests/async/test_metrics_client_async.py index a6336d486bd4..89757e75e37d 100644 --- a/sdk/monitor/azure-monitor-query/tests/async/test_metrics_client_async.py +++ b/sdk/monitor/azure-monitor-query/tests/async/test_metrics_client_async.py @@ -2,7 +2,7 @@ import pytest import os from azure.identity.aio import ClientSecretCredential -from azure.monitor.query import MetricAggregationType +from azure.monitor.query import MetricAggregationType, Metric from azure.monitor.query.aio import MetricsQueryClient def _credential(): @@ -42,6 +42,26 @@ async def test_metrics_granularity(): assert response assert response.granularity == timedelta(minutes=5) + +@pytest.mark.live_test_only +@pytest.mark.asyncio +async def test_metrics_list(): + credential = _credential() + client = MetricsQueryClient(credential) + response = await client.query_resource( + os.environ['METRICS_RESOURCE_URI'], + metric_names=["MatchedEventCount"], + timespan=timedelta(days=1), + granularity=timedelta(minutes=5), + aggregations=[MetricAggregationType.COUNT] + ) + assert response + metrics = response.metrics + assert len(metrics) == 1 + assert metrics[0].__class__ == Metric + assert metrics['MatchedEventCount'].__class__ == Metric + assert metrics['MatchedEventCount'] == metrics[0] + @pytest.mark.live_test_only @pytest.mark.asyncio async def test_metrics_namespaces(): diff --git a/sdk/monitor/azure-monitor-query/tests/test_metrics_client.py b/sdk/monitor/azure-monitor-query/tests/test_metrics_client.py index a4fa7cf726df..f9f5da4db012 100644 --- a/sdk/monitor/azure-monitor-query/tests/test_metrics_client.py +++ b/sdk/monitor/azure-monitor-query/tests/test_metrics_client.py @@ -2,7 +2,7 @@ import os from datetime import datetime, timedelta from azure.identity import ClientSecretCredential -from azure.monitor.query import MetricsQueryClient, MetricAggregationType +from azure.monitor.query import MetricsQueryClient, MetricAggregationType, Metric def _credential(): credential = ClientSecretCredential( @@ -39,6 +39,24 @@ def test_metrics_granularity(): assert response assert response.granularity == timedelta(minutes=5) +@pytest.mark.live_test_only +def test_metrics_list(): + credential = _credential() + client = MetricsQueryClient(credential) + response = client.query_resource( + os.environ['METRICS_RESOURCE_URI'], + metric_names=["MatchedEventCount"], + timespan=timedelta(days=1), + granularity=timedelta(minutes=5), + aggregations=[MetricAggregationType.COUNT] + ) + assert response + metrics = response.metrics + assert len(metrics) == 1 + assert metrics[0].__class__ == Metric + assert metrics['MatchedEventCount'].__class__ == Metric + assert metrics['MatchedEventCount'] == metrics[0] + @pytest.mark.live_test_only def test_metrics_namespaces(): client = MetricsQueryClient(_credential())