(prometheus) support label name completion

This commit is contained in:
Mitsuhiro Tanda
2017-09-06 20:50:32 +09:00
parent b349b3ef55
commit 40b74e6664
2 changed files with 102 additions and 8 deletions

View File

@@ -1,11 +1,15 @@
///<reference path="../../../headers/common.d.ts" />
import {PrometheusDatasource} from "./datasource";
import _ from 'lodash';
export class PromCompleter {
labelNameCache: any;
identifierRegexps = [/[\[\]a-zA-Z_0-9=]/];
constructor(private datasource: PrometheusDatasource) {
this.labelNameCache = {};
}
getCompletions(editor, session, pos, prefix, callback) {
@@ -13,14 +17,31 @@ export class PromCompleter {
switch (token.type) {
case 'label.name':
callback(null, ['instance', 'job'].map(function (key) {
return {
caption: key,
value: key,
meta: "label name",
score: Number.MAX_VALUE
};
}));
var metricName = this.findMetricName(session, pos.row, pos.column);
if (!metricName) {
callback(null, this.transformToCompletions(['__name__', 'instance', 'job']));
return;
}
if (this.labelNameCache[metricName]) {
callback(null, this.labelNameCache[metricName]);
return;
}
var op = '=~';
if (/[a-zA-Z_:][a-zA-Z0-9_:]*/.test(metricName)) {
op = '=';
}
var expr = '{__name__' + op + '"' + metricName + '"}';
this.datasource.performInstantQuery({ expr: expr }, new Date().getTime() / 1000).then(response => {
var labelNames = this.transformToCompletions(
_.uniq(_.flatten(response.data.data.result.map(r => {
return Object.keys(r.metric);
})))
);
this.labelNameCache[metricName] = labelNames;
callback(null, labelNames);
});
return;
case 'label.value':
callback(null, []);
@@ -57,4 +78,72 @@ export class PromCompleter {
});
}
transformToCompletions(words) {
return words.map(name => {
return {
caption: name,
value: name,
meta: "label name",
score: Number.MAX_VALUE
};
});
}
findMetricName(session, row, column) {
var metricName = '';
var tokens;
var nameLabelNameToken = this.findToken(session, row, column, 'label.name', '__name__', 'paren.lparen');
if (nameLabelNameToken) {
tokens = session.getTokens(nameLabelNameToken.row);
var nameLabelValueToken = tokens[nameLabelNameToken.index + 2];
if (nameLabelValueToken && nameLabelValueToken.type === 'label.value') {
metricName = nameLabelValueToken.value.slice(1, -1); // cut begin/end quotation
}
} else {
var metricNameToken = this.findToken(session, row, column, 'identifier', null, null);
if (metricNameToken) {
tokens = session.getTokens(metricNameToken.row);
if (tokens[metricNameToken.index + 1].type === 'paren.lparen') {
metricName = metricNameToken.value;
}
}
}
return metricName;
}
findToken(session, row, column, target, value, guard) {
var tokens, idx;
for (var r = row; r >= 0; r--) {
tokens = session.getTokens(r);
if (r === row) { // current row
var c = 0;
for (idx = 0; idx < tokens.length; idx++) {
c += tokens[idx].value.length;
if (c >= column) {
break;
}
}
} else {
idx = tokens.length - 1;
}
for (; idx >= 0; idx--) {
if (tokens[idx].type === guard) {
return null;
}
if (tokens[idx].type === target
&& (!value || tokens[idx].value === value)) {
tokens[idx].row = r;
tokens[idx].index = idx;
return tokens[idx];
}
}
}
return null;
}
}

View File

@@ -158,6 +158,11 @@ export class PrometheusDatasource {
return this._request('GET', url, query.requestId);
}
performInstantQuery(query, time) {
var url = '/api/v1/query?query=' + encodeURIComponent(query.expr) + '&time=' + time;
return this._request('GET', url, query.requestId);
}
performSuggestQuery(query, cache = false) {
var url = '/api/v1/label/__name__/values';