mirror of
https://github.com/grafana/grafana.git
synced 2025-09-25 16:54:15 +08:00
Loki: Fix Loki with repeated panels and interpolation for Explore (#21685)
This commit is contained in:
@ -276,7 +276,7 @@ export abstract class DataSourceApi<
|
|||||||
*/
|
*/
|
||||||
annotationQuery?(options: AnnotationQueryRequest<TQuery>): Promise<AnnotationEvent[]>;
|
annotationQuery?(options: AnnotationQueryRequest<TQuery>): Promise<AnnotationEvent[]>;
|
||||||
|
|
||||||
interpolateVariablesInQueries?(queries: TQuery[]): TQuery[];
|
interpolateVariablesInQueries?(queries: TQuery[], scopedVars: ScopedVars | {}): TQuery[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface MetadataInspectorProps<
|
export interface MetadataInspectorProps<
|
||||||
|
@ -52,6 +52,7 @@ export interface PanelModel<TOptions = any> {
|
|||||||
id: number;
|
id: number;
|
||||||
options: TOptions;
|
options: TOptions;
|
||||||
pluginVersion?: string;
|
pluginVersion?: string;
|
||||||
|
scopedVars?: ScopedVars;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -88,11 +88,12 @@ export async function getExploreUrl(args: GetExploreUrlArguments) {
|
|||||||
const range = timeSrv.timeRangeForUrl();
|
const range = timeSrv.timeRangeForUrl();
|
||||||
let state: Partial<ExploreUrlState> = { range };
|
let state: Partial<ExploreUrlState> = { range };
|
||||||
if (exploreDatasource.interpolateVariablesInQueries) {
|
if (exploreDatasource.interpolateVariablesInQueries) {
|
||||||
|
const scopedVars = panel.scopedVars || {};
|
||||||
state = {
|
state = {
|
||||||
...state,
|
...state,
|
||||||
datasource: exploreDatasource.name,
|
datasource: exploreDatasource.name,
|
||||||
context: 'explore',
|
context: 'explore',
|
||||||
queries: exploreDatasource.interpolateVariablesInQueries(exploreTargets),
|
queries: exploreDatasource.interpolateVariablesInQueries(exploreTargets, scopedVars),
|
||||||
};
|
};
|
||||||
} else {
|
} else {
|
||||||
state = {
|
state = {
|
||||||
|
@ -6,6 +6,7 @@ import {
|
|||||||
DataQueryRequest,
|
DataQueryRequest,
|
||||||
DataQueryResponse,
|
DataQueryResponse,
|
||||||
DataFrame,
|
DataFrame,
|
||||||
|
ScopedVars,
|
||||||
} from '@grafana/data';
|
} from '@grafana/data';
|
||||||
import { ElasticResponse } from './elastic_response';
|
import { ElasticResponse } from './elastic_response';
|
||||||
import { IndexPattern } from './index_pattern';
|
import { IndexPattern } from './index_pattern';
|
||||||
@ -263,14 +264,14 @@ export class ElasticDatasource extends DataSourceApi<ElasticsearchQuery, Elastic
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: ElasticsearchQuery[]): ElasticsearchQuery[] {
|
interpolateVariablesInQueries(queries: ElasticsearchQuery[], scopedVars: ScopedVars): ElasticsearchQuery[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length > 0) {
|
if (queries && queries.length > 0) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
query: this.templateSrv.replace(query.query, {}, 'lucene'),
|
query: this.templateSrv.replace(query.query, scopedVars, 'lucene'),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
@ -148,14 +148,14 @@ export class GraphiteDatasource extends DataSourceApi<GraphiteQuery, GraphiteOpt
|
|||||||
return tags;
|
return tags;
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: GraphiteQuery[]): GraphiteQuery[] {
|
interpolateVariablesInQueries(queries: GraphiteQuery[], scopedVars: ScopedVars): GraphiteQuery[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length > 0) {
|
if (queries && queries.length > 0) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
target: this.templateSrv.replace(query.target),
|
target: this.templateSrv.replace(query.target, scopedVars),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
|
|
||||||
import { dateMath, DataSourceApi, DataSourceInstanceSettings } from '@grafana/data';
|
import { dateMath, DataSourceApi, DataSourceInstanceSettings, ScopedVars } from '@grafana/data';
|
||||||
import InfluxSeries from './influx_series';
|
import InfluxSeries from './influx_series';
|
||||||
import InfluxQueryModel from './influx_query_model';
|
import InfluxQueryModel from './influx_query_model';
|
||||||
import ResponseParser from './response_parser';
|
import ResponseParser from './response_parser';
|
||||||
@ -167,7 +167,7 @@ export default class InfluxDatasource extends DataSourceApi<InfluxQuery, InfluxO
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: InfluxQuery[]): InfluxQuery[] {
|
interpolateVariablesInQueries(queries: InfluxQuery[], scopedVars: ScopedVars): InfluxQuery[] {
|
||||||
if (!queries || queries.length === 0) {
|
if (!queries || queries.length === 0) {
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
@ -178,11 +178,11 @@ export default class InfluxDatasource extends DataSourceApi<InfluxQuery, InfluxO
|
|||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
measurement: this.templateSrv.replace(query.measurement, null, 'regex'),
|
measurement: this.templateSrv.replace(query.measurement, scopedVars, 'regex'),
|
||||||
};
|
};
|
||||||
|
|
||||||
if (query.rawQuery) {
|
if (query.rawQuery) {
|
||||||
expandedQuery.query = this.templateSrv.replace(query.query, null, 'regex');
|
expandedQuery.query = this.templateSrv.replace(query.query, scopedVars, 'regex');
|
||||||
}
|
}
|
||||||
|
|
||||||
if (query.tags) {
|
if (query.tags) {
|
||||||
|
@ -35,6 +35,7 @@ import {
|
|||||||
DataQueryRequest,
|
DataQueryRequest,
|
||||||
DataQueryResponse,
|
DataQueryResponse,
|
||||||
AnnotationQueryRequest,
|
AnnotationQueryRequest,
|
||||||
|
ScopedVars,
|
||||||
} from '@grafana/data';
|
} from '@grafana/data';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
@ -128,7 +129,7 @@ export class LokiDatasource extends DataSourceApi<LokiQuery, LokiOptions> {
|
|||||||
.filter(target => target.expr && !target.hide)
|
.filter(target => target.expr && !target.hide)
|
||||||
.map(target => ({
|
.map(target => ({
|
||||||
...target,
|
...target,
|
||||||
expr: this.templateSrv.replace(target.expr, {}, this.interpolateQueryExpr),
|
expr: this.templateSrv.replace(target.expr, options.scopedVars, this.interpolateQueryExpr),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
if (options.exploreMode === ExploreMode.Metrics) {
|
if (options.exploreMode === ExploreMode.Metrics) {
|
||||||
@ -350,13 +351,13 @@ export class LokiDatasource extends DataSourceApi<LokiQuery, LokiOptions> {
|
|||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: LokiQuery[]): LokiQuery[] {
|
interpolateVariablesInQueries(queries: LokiQuery[], scopedVars: ScopedVars): LokiQuery[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length) {
|
if (queries && queries.length) {
|
||||||
expandedQueries = queries.map(query => ({
|
expandedQueries = queries.map(query => ({
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
expr: this.templateSrv.replace(query.expr, {}, this.interpolateQueryExpr),
|
expr: this.templateSrv.replace(query.expr, scopedVars, this.interpolateQueryExpr),
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
import ResponseParser from './response_parser';
|
import ResponseParser from './response_parser';
|
||||||
import { getBackendSrv } from '@grafana/runtime';
|
import { getBackendSrv } from '@grafana/runtime';
|
||||||
|
import { ScopedVars } from '@grafana/data';
|
||||||
import { TemplateSrv } from 'app/features/templating/template_srv';
|
import { TemplateSrv } from 'app/features/templating/template_srv';
|
||||||
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
||||||
//Types
|
//Types
|
||||||
@ -43,14 +44,17 @@ export class MssqlDatasource {
|
|||||||
return quotedValues.join(',');
|
return quotedValues.join(',');
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: MssqlQueryForInterpolation[]): MssqlQueryForInterpolation[] {
|
interpolateVariablesInQueries(
|
||||||
|
queries: MssqlQueryForInterpolation[],
|
||||||
|
scopedVars: ScopedVars
|
||||||
|
): MssqlQueryForInterpolation[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length > 0) {
|
if (queries && queries.length > 0) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
rawSql: this.templateSrv.replace(query.rawSql, {}, this.interpolateVariable),
|
rawSql: this.templateSrv.replace(query.rawSql, scopedVars, this.interpolateVariable),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
@ -2,6 +2,7 @@ import _ from 'lodash';
|
|||||||
import ResponseParser from './response_parser';
|
import ResponseParser from './response_parser';
|
||||||
import MysqlQuery from 'app/plugins/datasource/mysql/mysql_query';
|
import MysqlQuery from 'app/plugins/datasource/mysql/mysql_query';
|
||||||
import { getBackendSrv } from '@grafana/runtime';
|
import { getBackendSrv } from '@grafana/runtime';
|
||||||
|
import { ScopedVars } from '@grafana/data';
|
||||||
import { TemplateSrv } from 'app/features/templating/template_srv';
|
import { TemplateSrv } from 'app/features/templating/template_srv';
|
||||||
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
||||||
//Types
|
//Types
|
||||||
@ -27,7 +28,8 @@ export class MysqlDatasource {
|
|||||||
interpolateVariable = (value: string, variable: any) => {
|
interpolateVariable = (value: string, variable: any) => {
|
||||||
if (typeof value === 'string') {
|
if (typeof value === 'string') {
|
||||||
if (variable.multi || variable.includeAll) {
|
if (variable.multi || variable.includeAll) {
|
||||||
return this.queryModel.quoteLiteral(value);
|
const result = this.queryModel.quoteLiteral(value);
|
||||||
|
return result;
|
||||||
} else {
|
} else {
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
@ -43,14 +45,17 @@ export class MysqlDatasource {
|
|||||||
return quotedValues.join(',');
|
return quotedValues.join(',');
|
||||||
};
|
};
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: MysqlQueryForInterpolation[]): MysqlQueryForInterpolation[] {
|
interpolateVariablesInQueries(
|
||||||
|
queries: MysqlQueryForInterpolation[],
|
||||||
|
scopedVars: ScopedVars
|
||||||
|
): MysqlQueryForInterpolation[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length > 0) {
|
if (queries && queries.length > 0) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
rawSql: this.templateSrv.replace(query.rawSql, {}, this.interpolateVariable),
|
rawSql: this.templateSrv.replace(query.rawSql, scopedVars, this.interpolateVariable),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
@ -2,6 +2,7 @@ import _ from 'lodash';
|
|||||||
import ResponseParser from './response_parser';
|
import ResponseParser from './response_parser';
|
||||||
import PostgresQuery from 'app/plugins/datasource/postgres/postgres_query';
|
import PostgresQuery from 'app/plugins/datasource/postgres/postgres_query';
|
||||||
import { getBackendSrv } from '@grafana/runtime';
|
import { getBackendSrv } from '@grafana/runtime';
|
||||||
|
import { ScopedVars } from '@grafana/data';
|
||||||
import { TemplateSrv } from 'app/features/templating/template_srv';
|
import { TemplateSrv } from 'app/features/templating/template_srv';
|
||||||
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
import { TimeSrv } from 'app/features/dashboard/services/TimeSrv';
|
||||||
//Types
|
//Types
|
||||||
@ -49,14 +50,17 @@ export class PostgresDatasource {
|
|||||||
return quotedValues.join(',');
|
return quotedValues.join(',');
|
||||||
};
|
};
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: PostgresQueryForInterpolation[]): PostgresQueryForInterpolation[] {
|
interpolateVariablesInQueries(
|
||||||
|
queries: PostgresQueryForInterpolation[],
|
||||||
|
scopedVars: ScopedVars
|
||||||
|
): PostgresQueryForInterpolation[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length > 0) {
|
if (queries && queries.length > 0) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
rawSql: this.templateSrv.replace(query.rawSql, {}, this.interpolateVariable),
|
rawSql: this.templateSrv.replace(query.rawSql, scopedVars, this.interpolateVariable),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
@ -18,6 +18,7 @@ import {
|
|||||||
DataQueryResponseData,
|
DataQueryResponseData,
|
||||||
DataSourceApi,
|
DataSourceApi,
|
||||||
DataSourceInstanceSettings,
|
DataSourceInstanceSettings,
|
||||||
|
ScopedVars,
|
||||||
} from '@grafana/data';
|
} from '@grafana/data';
|
||||||
import { from, merge, Observable, of, forkJoin } from 'rxjs';
|
import { from, merge, Observable, of, forkJoin } from 'rxjs';
|
||||||
import { filter, map, tap } from 'rxjs/operators';
|
import { filter, map, tap } from 'rxjs/operators';
|
||||||
@ -608,14 +609,14 @@ export class PrometheusDatasource extends DataSourceApi<PromQuery, PromOptions>
|
|||||||
: { status: 'error', message: response.error };
|
: { status: 'error', message: response.error };
|
||||||
}
|
}
|
||||||
|
|
||||||
interpolateVariablesInQueries(queries: PromQuery[]): PromQuery[] {
|
interpolateVariablesInQueries(queries: PromQuery[], scopedVars: ScopedVars): PromQuery[] {
|
||||||
let expandedQueries = queries;
|
let expandedQueries = queries;
|
||||||
if (queries && queries.length) {
|
if (queries && queries.length) {
|
||||||
expandedQueries = queries.map(query => {
|
expandedQueries = queries.map(query => {
|
||||||
const expandedQuery = {
|
const expandedQuery = {
|
||||||
...query,
|
...query,
|
||||||
datasource: this.name,
|
datasource: this.name,
|
||||||
expr: templateSrv.replace(query.expr, {}, this.interpolateQueryExpr),
|
expr: templateSrv.replace(query.expr, scopedVars, this.interpolateQueryExpr),
|
||||||
};
|
};
|
||||||
return expandedQuery;
|
return expandedQuery;
|
||||||
});
|
});
|
||||||
|
Reference in New Issue
Block a user