Files
Josh Hunt 3c6e0e8ef8 Chore: ESlint import order (#44959)
* Add and configure eslint-plugin-import

* Fix the lint:ts npm command

* Autofix + prettier all the files

* Manually fix remaining files

* Move jquery code in jest-setup to external file to safely reorder imports

* Resolve issue caused by circular dependencies within Prometheus

* Update .betterer.results

* Fix missing // @ts-ignore

* ignore iconBundle.ts

* Fix missing // @ts-ignore
2022-04-22 14:33:13 +01:00

76 lines
2.7 KiB
TypeScript

import { lastValueFrom } from 'rxjs';
import { MetricFindValue, SelectableValue } from '@grafana/data';
import {
BucketAggregationType,
isBucketAggregationType,
} from '../components/QueryEditor/BucketAggregationsEditor/aggregations';
import { useDatasource, useRange } from '../components/QueryEditor/ElasticsearchQueryContext';
import {
isMetricAggregationType,
MetricAggregationType,
} from '../components/QueryEditor/MetricAggregationsEditor/aggregations';
type AggregationType = BucketAggregationType | MetricAggregationType;
const getFilter = (type: AggregationType) => {
if (isMetricAggregationType(type)) {
switch (type) {
case 'cardinality':
return [];
case 'top_metrics':
// top_metrics was introduced in 7.7 where `metrics` only supported number:
// https://www.elastic.co/guide/en/elasticsearch/reference/7.7/search-aggregations-metrics-top-metrics.html#_metrics
// TODO: starting from 7.11 it supports ips and keywords as well:
// https://www.elastic.co/guide/en/elasticsearch/reference/7.11/search-aggregations-metrics-top-metrics.html#_metrics
return ['number'];
default:
return ['number'];
}
}
if (isBucketAggregationType(type)) {
switch (type) {
case 'date_histogram':
return ['date'];
case 'geohash_grid':
return ['geo_point'];
case 'histogram':
return ['number'];
default:
return [];
}
}
return [];
};
const toSelectableValue = ({ text }: MetricFindValue): SelectableValue<string> => ({
label: text,
value: text,
});
/**
* Returns a function to query the configured datasource for autocomplete values for the specified aggregation type or data types.
* Each aggregation can be run on different types, for example avg only operates on numeric fields, geohash_grid only on geo_point fields.
* If an aggregation type is provided, the promise will resolve with all fields suitable to be used as a field for the given aggregation.
* If an array of types is providem the promise will resolve with all the fields matching the provided types.
* @param aggregationType the type of aggregation to get fields for
*/
export const useFields = (type: AggregationType | string[]) => {
const datasource = useDatasource();
const range = useRange();
const filter = Array.isArray(type) ? type : getFilter(type);
let rawFields: MetricFindValue[];
return async (q?: string) => {
// _mapping doesn't support filtering, we avoid sending a request everytime q changes
if (!rawFields) {
rawFields = await lastValueFrom(datasource.getFields(filter, range));
}
return rawFields.filter(({ text }) => q === undefined || text.includes(q)).map(toSelectableValue);
};
};