Support customising Prometheus queries

This commit adds support for adding optional prefix and/or suffix to
Prometheus queries.

For example, this can be used to perform vector matches between the
collected metric and another one, to gather additional metadata.

Change-Id: I725f0f5ad00b67f55bcacaf8447e050af3815c73
This commit is contained in:
Pierre Riteau 2022-01-10 15:20:29 +01:00
parent 0014fc507b
commit fe34ef9768
4 changed files with 33 additions and 1 deletions

View File

@ -18,6 +18,7 @@ from decimal import ROUND_HALF_UP
from oslo_config import cfg from oslo_config import cfg
from oslo_log import log from oslo_log import log
from voluptuous import All
from voluptuous import In from voluptuous import In
from voluptuous import Optional from voluptuous import Optional
from voluptuous import Required from voluptuous import Required
@ -83,7 +84,9 @@ PROMETHEUS_EXTRA_SCHEMA = {
'changes', 'delta', 'deriv', 'changes', 'delta', 'deriv',
'idelta', 'irange', 'irate', 'idelta', 'irange', 'irate',
'rate' 'rate'
]) ]),
Optional('query_prefix', default=''): All(str),
Optional('query_suffix', default=''): All(str),
} }
} }
@ -159,6 +162,8 @@ class PrometheusCollector(collector.BaseCollector):
'range_function') 'range_function')
groupby = self.conf[metric_name].get('groupby', []) groupby = self.conf[metric_name].get('groupby', [])
metadata = self.conf[metric_name].get('metadata', []) metadata = self.conf[metric_name].get('metadata', [])
query_prefix = self.conf[metric_name]['extra_args']['query_prefix']
query_suffix = self.conf[metric_name]['extra_args']['query_suffix']
period = tzutils.diff_seconds(end, start) period = tzutils.diff_seconds(end, start)
time = end time = end
@ -198,6 +203,14 @@ class PrometheusCollector(collector.BaseCollector):
', '.join(groupby + metadata) ', '.join(groupby + metadata)
) )
# Add custom query prefix
if query_prefix:
query = "{0} {1}".format(query_prefix, query)
# Add custom query suffix
if query_suffix:
query = "{0} {1}".format(query, query_suffix)
try: try:
res = self._conn.get_instant( res = self._conn.get_instant(
query, query,

View File

@ -135,6 +135,8 @@ class MetricConfigValidationTest(tests.TestCase):
expected_output['metric_one']['groupby'].append('project_id') expected_output['metric_one']['groupby'].append('project_id')
expected_output['metric_one']['extra_args'] = { expected_output['metric_one']['extra_args'] = {
'aggregation_method': 'max', 'aggregation_method': 'max',
'query_prefix': '',
'query_suffix': '',
} }
self.assertEqual( self.assertEqual(
collector.prometheus.PrometheusCollector.check_configuration(data), collector.prometheus.PrometheusCollector.check_configuration(data),
@ -147,6 +149,8 @@ class MetricConfigValidationTest(tests.TestCase):
expected_output['metric_one']['groupby'].append('project_id') expected_output['metric_one']['groupby'].append('project_id')
expected_output['metric_one']['extra_args'] = { expected_output['metric_one']['extra_args'] = {
'aggregation_method': 'max', 'aggregation_method': 'max',
'query_prefix': '',
'query_suffix': '',
} }
self.assertEqual( self.assertEqual(
collector.prometheus.PrometheusCollector.check_configuration(data), collector.prometheus.PrometheusCollector.check_configuration(data),
@ -158,6 +162,8 @@ class MetricConfigValidationTest(tests.TestCase):
data['metrics']['metric_one']['extra_args'] = { data['metrics']['metric_one']['extra_args'] = {
'aggregation_method': 'max', 'aggregation_method': 'max',
'query_function': 'abs', 'query_function': 'abs',
'query_prefix': 'custom_prefix',
'query_suffix': 'custom_suffix',
'range_function': 'delta', 'range_function': 'delta',
} }
expected_output = copy.deepcopy(self.base_output) expected_output = copy.deepcopy(self.base_output)
@ -165,6 +171,8 @@ class MetricConfigValidationTest(tests.TestCase):
expected_output['metric_one']['extra_args'] = { expected_output['metric_one']['extra_args'] = {
'aggregation_method': 'max', 'aggregation_method': 'max',
'query_function': 'abs', 'query_function': 'abs',
'query_prefix': 'custom_prefix',
'query_suffix': 'custom_suffix',
'range_function': 'delta', 'range_function': 'delta',
} }

View File

@ -359,6 +359,12 @@ Prometheus
``log10``, ``round``, ``sqrt``. For more information on these functions, ``log10``, ``round``, ``sqrt``. For more information on these functions,
you can check `this page`_ you can check `this page`_
* ``query_prefix``: Optional argument. An arbitrary prefix to add to the
Prometheus query generated by CloudKitty, separated by a space.
* ``query_suffix``: Optional argument. An arbitrary suffix to add to the
Prometheus query generated by CloudKitty, separated by a space.
* ``range_function``: Optional argument. The function to apply instead of the * ``range_function``: Optional argument. The function to apply instead of the
implicit ``{aggregation_method}_over_time``. Must be one of ``changes``, implicit ``{aggregation_method}_over_time``. Must be one of ``changes``,
``delta``, ``deriv``, ``idelta``, ``irange``, ``irate``, ``rate``. For more ``delta``, ``deriv``, ``idelta``, ``irange``, ``irate``, ``rate``. For more

View File

@ -0,0 +1,5 @@
---
features:
- |
Adds support for specifying optional prefix and/or suffix to add to
Prometheus queries.