Vehicle-Anti-Theft-Face-Rec.../venv/Lib/site-packages/gcloud/monitoring/metric.py

345 lines
12 KiB
Python

# Copyright 2016 Google Inc. All rights reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""Metric Descriptors for the `Google Monitoring API (V3)`_.
.. _Google Monitoring API (V3):
https://cloud.google.com/monitoring/api/ref_v3/rest/v3/\
projects.metricDescriptors
"""
import collections
from gcloud.monitoring.label import LabelDescriptor
class MetricKind(object):
"""Choices for the `kind of measurement`_.
.. _kind of measurement:
https://cloud.google.com/monitoring/api/ref_v3/rest/v3/\
projects.metricDescriptors#MetricKind
"""
METRIC_KIND_UNSPECIFIED = 'METRIC_KIND_UNSPECIFIED'
""".. note:: An unspecified kind is not allowed in metric descriptors."""
GAUGE = 'GAUGE'
DELTA = 'DELTA'
CUMULATIVE = 'CUMULATIVE'
class ValueType(object):
"""Choices for the `metric value type`_.
.. _metric value type:
https://cloud.google.com/monitoring/api/ref_v3/rest/v3/\
projects.metricDescriptors#ValueType
"""
VALUE_TYPE_UNSPECIFIED = 'VALUE_TYPE_UNSPECIFIED'
""".. note:: An unspecified type is not allowed in metric descriptors."""
BOOL = 'BOOL'
INT64 = 'INT64'
DOUBLE = 'DOUBLE'
STRING = 'STRING'
DISTRIBUTION = 'DISTRIBUTION'
class MetricDescriptor(object):
"""Specification of a metric type and its schema.
The preferred way to construct a metric descriptor object is using the
:meth:`~gcloud.monitoring.client.Client.metric_descriptor` factory method
of the :class:`~gcloud.monitoring.client.Client` class.
:type client: :class:`gcloud.monitoring.client.Client`
:param client: A client for operating on the metric descriptor.
:type type_: string
:param type_:
The metric type including a DNS name prefix. For example:
``"compute.googleapis.com/instance/cpu/utilization"``
:type metric_kind: string
:param metric_kind:
The kind of measurement. It must be one of
:data:`MetricKind.GAUGE`, :data:`MetricKind.DELTA`,
or :data:`MetricKind.CUMULATIVE`. See :class:`MetricKind`.
:type value_type: string
:param value_type:
The value type of the metric. It must be one of
:data:`ValueType.BOOL`, :data:`ValueType.INT64`,
:data:`ValueType.DOUBLE`, :data:`ValueType.STRING`,
or :data:`ValueType.DISTRIBUTION`.
See :class:`ValueType`.
:type labels: list of :class:`~gcloud.monitoring.label.LabelDescriptor`
:param labels:
A sequence of zero or more label descriptors specifying the labels
used to identify a specific instance of this metric.
:type unit: string
:param unit: An optional unit in which the metric value is reported.
:type description: string
:param description: An optional detailed description of the metric.
:type display_name: string
:param display_name: An optional concise name for the metric.
:type name: string or None
:param name:
The "resource name" of the metric descriptor. For example:
``"projects/<project_id>/metricDescriptors/<type>"``. As
retrieved from the service, this will always be specified.
You can and should omit it when constructing an instance for
the purpose of creating a new metric descriptor.
"""
def __init__(self, client, type_,
metric_kind=MetricKind.METRIC_KIND_UNSPECIFIED,
value_type=ValueType.VALUE_TYPE_UNSPECIFIED,
labels=(),
unit='', description='', display_name='',
name=None):
self.client = client
self.name = name
self.type = type_
self.labels = labels
self.metric_kind = metric_kind
self.value_type = value_type
self.unit = unit
self.description = description
self.display_name = display_name
def create(self):
"""Create a new metric descriptor based on this object.
Example::
>>> descriptor = client.metric_descriptor(
... 'custom.googleapis.com/my_metric',
... metric_kind=MetricKind.GAUGE,
... value_type=ValueType.DOUBLE,
... description='This is a simple example of a custom metric.')
>>> descriptor.create()
The metric kind must not be :data:`MetricKind.METRIC_KIND_UNSPECIFIED`,
and the value type must not be
:data:`ValueType.VALUE_TYPE_UNSPECIFIED`.
The ``name`` attribute is ignored in preparing the creation request.
All attributes are overwritten by the values received in the response
(normally affecting only ``name``).
"""
path = '/projects/{project}/metricDescriptors/'.format(
project=self.client.project)
response = self.client.connection.api_request(method='POST', path=path,
data=self._to_dict())
self._init_from_dict(response)
def delete(self):
"""Delete the metric descriptor identified by this object.
Example::
>>> descriptor = client.metric_descriptor(
... 'custom.googleapis.com/my_metric')
>>> descriptor.delete()
Only the ``client`` and ``type`` attributes are used.
"""
path = '/projects/{project}/metricDescriptors/{type}'.format(
project=self.client.project,
type=self.type)
self.client.connection.api_request(method='DELETE', path=path)
@classmethod
def _fetch(cls, client, metric_type):
"""Look up a metric descriptor by type.
:type client: :class:`gcloud.monitoring.client.Client`
:param client: The client to use.
:type metric_type: string
:param metric_type: The metric type name.
:rtype: :class:`MetricDescriptor`
:returns: The metric descriptor instance.
:raises: :class:`gcloud.exceptions.NotFound` if the metric descriptor
is not found.
"""
path = '/projects/{project}/metricDescriptors/{type}'.format(
project=client.project,
type=metric_type)
info = client.connection.api_request(method='GET', path=path)
return cls._from_dict(client, info)
@classmethod
def _list(cls, client, filter_string=None, type_prefix=None):
"""List all metric descriptors for the project.
:type client: :class:`gcloud.monitoring.client.Client`
:param client: The client to use.
:type filter_string: string or None
:param filter_string:
An optional filter expression describing the metric descriptors
to be returned. See the `filter documentation`_.
:type type_prefix: string or None
:param type_prefix: An optional prefix constraining the selected
metric types. This adds ``metric.type = starts_with("<prefix>")``
to the filter.
:rtype: list of :class:`MetricDescriptor`
:returns: A list of metric descriptor instances.
.. _filter documentation:
https://cloud.google.com/monitoring/api/v3/filters
"""
path = '/projects/{project}/metricDescriptors/'.format(
project=client.project)
filters = []
if filter_string is not None:
filters.append(filter_string)
if type_prefix is not None:
filters.append('metric.type = starts_with("{prefix}")'.format(
prefix=type_prefix))
descriptors = []
page_token = None
while True:
params = {}
if filters:
params['filter'] = ' AND '.join(filters)
if page_token is not None:
params['pageToken'] = page_token
response = client.connection.api_request(
method='GET', path=path, query_params=params)
for info in response.get('metricDescriptors', ()):
descriptors.append(cls._from_dict(client, info))
page_token = response.get('nextPageToken')
if not page_token:
break
return descriptors
@classmethod
def _from_dict(cls, client, info):
"""Construct a metric descriptor from the parsed JSON representation.
:type client: :class:`gcloud.monitoring.client.Client`
:param client: A client to be included in the returned object.
:type info: dict
:param info:
A ``dict`` parsed from the JSON wire-format representation.
:rtype: :class:`MetricDescriptor`
:returns: A metric descriptor.
"""
descriptor = cls(client, None)
descriptor._init_from_dict(info)
return descriptor
def _init_from_dict(self, info):
"""Initialize attributes from the parsed JSON representation.
:type info: dict
:param info:
A ``dict`` parsed from the JSON wire-format representation.
"""
self.name = info['name']
self.type = info['type']
self.labels = tuple(LabelDescriptor._from_dict(label)
for label in info.get('labels', []))
self.metric_kind = info['metricKind']
self.value_type = info['valueType']
self.unit = info.get('unit', '')
self.description = info.get('description', '')
self.display_name = info.get('displayName', '')
def _to_dict(self):
"""Build a dictionary ready to be serialized to the JSON wire format.
:rtype: dict
:returns: A dictionary.
"""
info = {
'type': self.type,
'metricKind': self.metric_kind,
'valueType': self.value_type,
}
if self.labels:
info['labels'] = [label._to_dict() for label in self.labels]
if self.unit:
info['unit'] = self.unit
if self.description:
info['description'] = self.description
if self.display_name:
info['displayName'] = self.display_name
return info
def __repr__(self):
return (
'<MetricDescriptor:\n'
' name={name!r},\n'
' type={type!r},\n'
' metric_kind={metric_kind!r}, value_type={value_type!r},\n'
' labels={labels!r},\n'
' display_name={display_name!r}, unit={unit!r},\n'
' description={description!r}>'
).format(**self.__dict__)
class Metric(collections.namedtuple('Metric', 'type labels')):
"""A specific metric identified by specifying values for all labels.
:type type: string
:param type: The metric type name.
:type labels: dict
:param labels: A mapping from label names to values for all labels
enumerated in the associated :class:`MetricDescriptor`.
"""
__slots__ = ()
@classmethod
def _from_dict(cls, info):
"""Construct a metric object from the parsed JSON representation.
:type info: dict
:param info:
A ``dict`` parsed from the JSON wire-format representation.
:rtype: :class:`Metric`
:returns: A metric object.
"""
return cls(
type=info['type'],
labels=info.get('labels', {}),
)