mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
LogContext: Fix structured metadata labels being added as stream selectors (#86825)
* LogContext: Fix structured metadata labels being added as stream selectors * use row index
This commit is contained in:
parent
0fa983ad8e
commit
a8424f4831
@ -37,6 +37,11 @@ const defaultLogRow = {
|
||||
type: FieldType.time,
|
||||
values: [0],
|
||||
},
|
||||
{
|
||||
name: 'labelTypes',
|
||||
type: FieldType.other,
|
||||
values: [{ bar: 'I', foo: 'S', xyz: 'I' }],
|
||||
},
|
||||
],
|
||||
}),
|
||||
labels: { bar: 'baz', foo: 'uniqueParsedLabel', xyz: 'abc' },
|
||||
@ -75,7 +80,7 @@ describe('LogContextProvider', () => {
|
||||
);
|
||||
expect(logContextProvider.getInitContextFilters).toBeCalled();
|
||||
expect(logContextProvider.getInitContextFilters).toHaveBeenCalledWith(
|
||||
{ bar: 'baz', foo: 'uniqueParsedLabel', xyz: 'abc' },
|
||||
expect.objectContaining({ labels: { bar: 'baz', foo: 'uniqueParsedLabel', xyz: 'abc' } }),
|
||||
{ expr: '{bar="baz"}', refId: 'A' },
|
||||
{
|
||||
from: dateTime(defaultLogRow.timeEpochMs),
|
||||
@ -399,7 +404,7 @@ describe('LogContextProvider', () => {
|
||||
};
|
||||
|
||||
it('should correctly create contextFilters', async () => {
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithoutParser);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow, queryWithoutParser);
|
||||
expect(result.contextFilters).toEqual([
|
||||
{ enabled: true, nonIndexed: false, label: 'bar', value: 'baz' },
|
||||
{ enabled: false, nonIndexed: true, label: 'foo', value: 'uniqueParsedLabel' },
|
||||
@ -409,28 +414,29 @@ describe('LogContextProvider', () => {
|
||||
});
|
||||
|
||||
it('should return empty contextFilters if no query', async () => {
|
||||
const filters = (await logContextProvider.getInitContextFilters(defaultLogRow.labels, undefined))
|
||||
.contextFilters;
|
||||
const filters = (await logContextProvider.getInitContextFilters(defaultLogRow, undefined)).contextFilters;
|
||||
expect(filters).toEqual([]);
|
||||
});
|
||||
|
||||
it('should return empty contextFilters if no labels', async () => {
|
||||
const filters = (await logContextProvider.getInitContextFilters({}, queryWithoutParser)).contextFilters;
|
||||
const filters = (
|
||||
await logContextProvider.getInitContextFilters({ labels: [] } as unknown as LogRowModel, queryWithoutParser)
|
||||
).contextFilters;
|
||||
expect(filters).toEqual([]);
|
||||
});
|
||||
|
||||
it('should call fetchSeriesLabels if parser', async () => {
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser);
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser);
|
||||
expect(defaultLanguageProviderMock.fetchSeriesLabels).toBeCalled();
|
||||
});
|
||||
|
||||
it('should call fetchSeriesLabels with given time range', async () => {
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser, timeRange);
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser, timeRange);
|
||||
expect(defaultLanguageProviderMock.fetchSeriesLabels).toBeCalledWith(`{bar="baz"}`, { timeRange });
|
||||
});
|
||||
|
||||
it('should call `languageProvider.start` if no parser with given time range', async () => {
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithoutParser, timeRange);
|
||||
await logContextProvider.getInitContextFilters(defaultLogRow, queryWithoutParser, timeRange);
|
||||
expect(defaultLanguageProviderMock.start).toBeCalledWith(timeRange);
|
||||
});
|
||||
});
|
||||
@ -442,7 +448,7 @@ describe('LogContextProvider', () => {
|
||||
};
|
||||
|
||||
it('should correctly create contextFilters', async () => {
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser);
|
||||
expect(result.contextFilters).toEqual([
|
||||
{ enabled: true, nonIndexed: false, label: 'bar', value: 'baz' },
|
||||
{ enabled: false, nonIndexed: true, label: 'foo', value: 'uniqueParsedLabel' },
|
||||
@ -452,13 +458,14 @@ describe('LogContextProvider', () => {
|
||||
});
|
||||
|
||||
it('should return empty contextFilters if no query', async () => {
|
||||
const filters = (await logContextProvider.getInitContextFilters(defaultLogRow.labels, undefined))
|
||||
.contextFilters;
|
||||
const filters = (await logContextProvider.getInitContextFilters(defaultLogRow, undefined)).contextFilters;
|
||||
expect(filters).toEqual([]);
|
||||
});
|
||||
|
||||
it('should return empty contextFilters if no labels', async () => {
|
||||
const filters = (await logContextProvider.getInitContextFilters({}, queryWithParser)).contextFilters;
|
||||
const filters = (
|
||||
await logContextProvider.getInitContextFilters({ labels: [] } as unknown as LogRowModel, queryWithParser)
|
||||
).contextFilters;
|
||||
expect(filters).toEqual([]);
|
||||
});
|
||||
});
|
||||
@ -477,7 +484,7 @@ describe('LogContextProvider', () => {
|
||||
selectedExtractedLabels: ['foo'],
|
||||
})
|
||||
);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser);
|
||||
expect(result.contextFilters).toEqual([
|
||||
{ enabled: false, nonIndexed: false, label: 'bar', value: 'baz' }, // disabled real label
|
||||
{ enabled: true, nonIndexed: true, label: 'foo', value: 'uniqueParsedLabel' }, // enabled parsed label
|
||||
@ -494,7 +501,7 @@ describe('LogContextProvider', () => {
|
||||
selectedExtractedLabels: ['foo'],
|
||||
})
|
||||
);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser);
|
||||
expect(result.contextFilters).toEqual([
|
||||
{ enabled: true, nonIndexed: false, label: 'bar', value: 'baz' }, // enabled real label
|
||||
{ enabled: false, nonIndexed: true, label: 'foo', value: 'uniqueParsedLabel' },
|
||||
@ -511,7 +518,7 @@ describe('LogContextProvider', () => {
|
||||
selectedExtractedLabels: ['foo', 'new'],
|
||||
})
|
||||
);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow.labels, queryWithParser);
|
||||
const result = await logContextProvider.getInitContextFilters(defaultLogRow, queryWithParser);
|
||||
expect(result.contextFilters).toEqual([
|
||||
{ enabled: false, nonIndexed: false, label: 'bar', value: 'baz' },
|
||||
{ enabled: true, nonIndexed: true, label: 'foo', value: 'uniqueParsedLabel' },
|
||||
|
@ -16,11 +16,10 @@ import {
|
||||
dateTime,
|
||||
} from '@grafana/data';
|
||||
import { LabelParser, LabelFilter, LineFilters, PipelineStage, Logfmt, Json } from '@grafana/lezer-logql';
|
||||
import { Labels } from '@grafana/schema';
|
||||
|
||||
import { LokiContextUi } from './components/LokiContextUi';
|
||||
import { LokiDatasource, makeRequest, REF_ID_STARTER_LOG_ROW_CONTEXT } from './datasource';
|
||||
import { escapeLabelValueInExactSelector } from './languageUtils';
|
||||
import { escapeLabelValueInExactSelector, getLabelTypeFromFrame } from './languageUtils';
|
||||
import { addLabelToQuery, addParserToQuery } from './modifyQuery';
|
||||
import {
|
||||
getNodePositionsFromQuery,
|
||||
@ -61,7 +60,7 @@ export class LogContextProvider {
|
||||
// to use the cached filters, we need to reinitialize them.
|
||||
if (this.cachedContextFilters.length === 0 || !cacheFilters) {
|
||||
const filters = (
|
||||
await this.getInitContextFilters(row.labels, origQuery, {
|
||||
await this.getInitContextFilters(row, origQuery, {
|
||||
from: dateTime(row.timeEpochMs),
|
||||
to: dateTime(row.timeEpochMs),
|
||||
raw: { from: dateTime(row.timeEpochMs), to: dateTime(row.timeEpochMs) },
|
||||
@ -312,14 +311,15 @@ export class LogContextProvider {
|
||||
};
|
||||
|
||||
getInitContextFilters = async (
|
||||
labels: Labels,
|
||||
row: LogRowModel,
|
||||
query?: LokiQuery,
|
||||
timeRange?: TimeRange
|
||||
): Promise<{ contextFilters: ContextFilter[]; preservedFiltersApplied: boolean }> => {
|
||||
let preservedFiltersApplied = false;
|
||||
if (!query || isEmpty(labels)) {
|
||||
if (!query || isEmpty(row.labels)) {
|
||||
return { contextFilters: [], preservedFiltersApplied };
|
||||
}
|
||||
const rowLabels = row.labels;
|
||||
|
||||
// 1. First we need to get all labels from the log row's label
|
||||
// and correctly set parsed and not parsed labels
|
||||
@ -338,12 +338,12 @@ export class LogContextProvider {
|
||||
}
|
||||
|
||||
const contextFilters: ContextFilter[] = [];
|
||||
Object.entries(labels).forEach(([label, value]) => {
|
||||
Object.entries(rowLabels).forEach(([label, value]) => {
|
||||
const filter: ContextFilter = {
|
||||
label,
|
||||
value: value,
|
||||
enabled: allLabels.includes(label),
|
||||
nonIndexed: !allLabels.includes(label),
|
||||
nonIndexed: getLabelTypeFromFrame(label, row.dataFrame, row.rowIndex) !== LabelType.Indexed,
|
||||
};
|
||||
|
||||
contextFilters.push(filter);
|
||||
|
@ -122,7 +122,7 @@ describe('LokiContextUi', () => {
|
||||
render(<LokiContextUi {...props} />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(props.logContextProvider.getInitContextFilters).toHaveBeenCalledWith(props.row.labels, props.origQuery, {
|
||||
expect(props.logContextProvider.getInitContextFilters).toHaveBeenCalledWith(props.row, props.origQuery, {
|
||||
from: dateTime(props.row.timeEpochMs),
|
||||
to: dateTime(props.row.timeEpochMs),
|
||||
raw: { from: dateTime(props.row.timeEpochMs), to: dateTime(props.row.timeEpochMs) },
|
||||
|
@ -205,7 +205,7 @@ export function LokiContextUi(props: LokiContextUiProps) {
|
||||
|
||||
useAsync(async () => {
|
||||
setLoading(true);
|
||||
const initContextFilters = await logContextProvider.getInitContextFilters(row.labels, origQuery, {
|
||||
const initContextFilters = await logContextProvider.getInitContextFilters(row, origQuery, {
|
||||
from: dateTime(row.timeEpochMs),
|
||||
to: dateTime(row.timeEpochMs),
|
||||
raw: { from: dateTime(row.timeEpochMs), to: dateTime(row.timeEpochMs) },
|
||||
|
Loading…
Reference in New Issue
Block a user