diff --git a/packages/jaeger-ui/src/constants/default-config.tsx b/packages/jaeger-ui/src/constants/default-config.tsx index a7b332cb89..ac133f849e 100644 --- a/packages/jaeger-ui/src/constants/default-config.tsx +++ b/packages/jaeger-ui/src/constants/default-config.tsx @@ -66,6 +66,7 @@ export default deepFreeze( gaID: null, trackErrors: true, }, + topTagPrefixes: ['http.'], }, // fields that should be individually merged vs wholesale replaced '__mergeFields', diff --git a/packages/jaeger-ui/src/model/transform-trace-data.test.js b/packages/jaeger-ui/src/model/transform-trace-data.test.js new file mode 100644 index 0000000000..a0f1164964 --- /dev/null +++ b/packages/jaeger-ui/src/model/transform-trace-data.test.js @@ -0,0 +1,31 @@ +// Copyright (c) 2019 The Jaeger Authors. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +import { orderTags } from './transform-trace-data'; + +it('correctly orders tags', () => { + const orderedTags = orderTags( + [ + { key: 'b.ip', value: '8.8.4.4' }, + { key: 'http.status_code', value: '200' }, + { key: 'a.ip', value: '8.8.8.8' }, + ], + ['http.'] + ); + expect(orderedTags).toEqual([ + { key: 'http.status_code', value: '200' }, + { key: 'a.ip', value: '8.8.8.8' }, + { key: 'b.ip', value: '8.8.4.4' }, + ]); +}); diff --git a/packages/jaeger-ui/src/model/transform-trace-data.tsx b/packages/jaeger-ui/src/model/transform-trace-data.tsx index db98ea7a7c..8a20818b75 100644 --- a/packages/jaeger-ui/src/model/transform-trace-data.tsx +++ b/packages/jaeger-ui/src/model/transform-trace-data.tsx @@ -15,6 +15,7 @@ import _isEqual from 'lodash/isEqual'; import { getTraceSpanIdsAsTree } from '../selectors/trace'; +import { getConfigValue } from '../utils/config/get-config'; import { KeyValuePair, Span, SpanData, Trace, TraceData } from '../types/trace'; import TreeNode from '../utils/TreeNode'; @@ -32,6 +33,24 @@ function deduplicateTags(spanTags: Array) { return { tags, warnings }; } +export function orderTags(spanTags: Array, topPrefixes: Array) { + const orderedTags: Array = [...spanTags]; + orderedTags.sort((a, b) => { + for (let i = 0; i < (topPrefixes).length; i++) { + const p = topPrefixes[i]; + if (a.key.startsWith(p) && !b.key.startsWith(p)) { + return -1; + } + + if (!a.key.startsWith(p) && b.key.startsWith(p)) { + return 1; + } + } + return a.key.localeCompare(b.key); + }); + return orderedTags; +} + /** * NOTE: Mutates `data` - Transform the HTTP response data into the form the app * generally requires. @@ -109,10 +128,7 @@ export default function transformTraceData(data: TraceData & { spans: SpanData[] span.tags = span.tags || []; span.references = span.references || []; const tagsInfo = deduplicateTags(span.tags); - tagsInfo.tags.sort((a, b) => { - return a.key.localeCompare(b.key); - }); - span.tags = tagsInfo.tags; + span.tags = orderTags(tagsInfo.tags, getConfigValue('topTagPrefixes') || []); span.warnings = span.warnings.concat(tagsInfo.warnings); span.references.forEach(ref => { const refSpan = spanMap.get(ref.spanID) as Span; diff --git a/packages/jaeger-ui/src/types/config.tsx b/packages/jaeger-ui/src/types/config.tsx index 9527b7c068..683c82a134 100644 --- a/packages/jaeger-ui/src/types/config.tsx +++ b/packages/jaeger-ui/src/types/config.tsx @@ -36,6 +36,7 @@ export type Config = { menu: (ConfigMenuGroup | ConfigMenuItem)[]; search?: { maxLookback: { label: string; value: string } }; scripts?: TScript[]; + topTagPrefixes?: string[]; tracking?: { gaID: string | TNil; trackErrors: boolean | TNil;