The open and composable observability and data visualization platform. Visualize metrics, logs, and traces from multiple sources like Prometheus, Loki, Elasticsearch, InfluxDB, Postgres and many more.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
grafana/public/app/plugins/datasource/stackdriver/StackdriverMetricFindQuery.ts

115 lines
3.8 KiB

import has from 'lodash/has';
import isString from 'lodash/isString';
import { alignmentPeriods } from './constants';
import { MetricFindQueryTypes } from './types';
import {
extractServicesFromMetricDescriptors,
getMetricTypesByService,
getAlignmentOptionsByMetric,
getAggregationOptionsByMetric,
} from './functions';
export default class StackdriverMetricFindQuery {
constructor(private datasource) {}
async query(query: any) {
try {
switch (query.selectedQueryType) {
case MetricFindQueryTypes.Services:
return this.handleServiceQuery();
case MetricFindQueryTypes.MetricTypes:
return this.handleMetricTypesQuery(query);
case MetricFindQueryTypes.MetricLabels:
case MetricFindQueryTypes.ResourceLabels:
return this.handleLabelQuery(query);
case MetricFindQueryTypes.ResourceTypes:
return this.handleResourceTypeQuery(query);
case MetricFindQueryTypes.Alignerns:
return this.handleAlignersQuery(query);
case MetricFindQueryTypes.AlignmentPeriods:
return this.handleAlignmentPeriodQuery();
case MetricFindQueryTypes.Aggregations:
return this.handleAggregationQuery(query);
default:
return [];
}
} catch (error) {
console.error(`Could not run StackdriverMetricFindQuery ${query}`, error);
return [];
}
}
async handleServiceQuery() {
const metricDescriptors = await this.datasource.getMetricTypes(this.datasource.projectName);
const services = extractServicesFromMetricDescriptors(metricDescriptors);
return services.map(s => ({
text: s.serviceShortName,
value: s.name,
expandable: true,
}));
}
async handleMetricTypesQuery({ selectedService }) {
if (!selectedService) {
return [];
}
const metricDescriptors = await this.datasource.getMetricTypes(this.datasource.projectName);
return getMetricTypesByService(metricDescriptors, selectedService).map(s => ({
text: s.displayName,
value: s.name,
expandable: true,
}));
}
async handleLabelQuery({ selectedQueryType, selectedMetricType, labelKey }) {
if (!selectedMetricType) {
return [];
}
const refId = 'handleLabelsQueryType';
const response = await this.datasource.getLabels(selectedMetricType, refId);
if (!has(response, `meta.${selectedQueryType}.${labelKey}`)) {
return [];
}
return response.meta[selectedQueryType][labelKey].map(this.toFindQueryResult);
}
async handleResourceTypeQuery({ selectedMetricType }) {
if (!selectedMetricType) {
return [];
}
try {
const refId = 'handleResourceTypeQueryQueryType';
const response = await this.datasource.getLabels(selectedMetricType, refId);
return response.meta.resourceTypes.map(this.toFindQueryResult);
} catch (error) {
return [];
}
}
async handleAlignersQuery({ selectedMetricType }) {
if (!selectedMetricType) {
return [];
}
const metricDescriptors = await this.datasource.getMetricTypes(this.datasource.projectName);
const { valueType, metricKind } = metricDescriptors.find(m => m.type === selectedMetricType);
return getAlignmentOptionsByMetric(valueType, metricKind).map(this.toFindQueryResult);
}
async handleAggregationQuery({ selectedMetricType }) {
if (!selectedMetricType) {
return [];
}
const metricDescriptors = await this.datasource.getMetricTypes(this.datasource.projectName);
const { valueType, metricKind } = metricDescriptors.find(m => m.type === selectedMetricType);
return getAggregationOptionsByMetric(valueType, metricKind).map(this.toFindQueryResult);
}
handleAlignmentPeriodQuery() {
return alignmentPeriods.map(this.toFindQueryResult);
}
toFindQueryResult(x) {
return isString(x) ? { text: x, expandable: true } : { ...x, expandable: true };
}
}