diff --git a/public/app/angular/angular_wrappers.ts b/public/app/angular/angular_wrappers.ts index 3b02e5ddbeb..be939278a09 100644 --- a/public/app/angular/angular_wrappers.ts +++ b/public/app/angular/angular_wrappers.ts @@ -22,7 +22,6 @@ import { MetricSelect } from '../core/components/Select/MetricSelect'; import { TagFilter } from '../core/components/TagFilter/TagFilter'; import { HelpModal } from '../core/components/help/HelpModal'; import { SearchField, SearchResults, SearchResultsFilter } from '../features/search'; -import { LokiAnnotationsQueryEditor } from '../plugins/datasource/loki/components/AnnotationsQueryEditor'; const { SecretFormField } = LegacyForms; @@ -143,13 +142,6 @@ export function registerAngularDirectives() { ['onChange', { watchDepth: 'reference', wrapApply: true }], ]); - react2AngularDirective('lokiAnnotationsQueryEditor', LokiAnnotationsQueryEditor, [ - 'expr', - 'maxLines', - 'instant', - 'onChange', - ['datasource', { watchDepth: 'reference' }], - ]); react2AngularDirective('datasourceHttpSettingsNext', DataSourceHttpSettings, [ 'defaultUrl', 'showAccessOptions', diff --git a/public/app/features/annotations/standardAnnotationSupport.ts b/public/app/features/annotations/standardAnnotationSupport.ts index 04a4906b4ad..743cb79be39 100644 --- a/public/app/features/annotations/standardAnnotationSupport.ts +++ b/public/app/features/annotations/standardAnnotationSupport.ts @@ -236,7 +236,7 @@ export function getAnnotationsFromData( */ export function shouldUseMappingUI(datasource: DataSourceApi): boolean { const { type } = datasource; - return type !== 'prometheus' && type !== 'elasticsearch'; + return type !== 'prometheus' && type !== 'elasticsearch' && type !== 'loki'; } /** @@ -244,5 +244,5 @@ export function shouldUseMappingUI(datasource: DataSourceApi): boolean { */ export function shouldUseLegacyRunner(datasource: DataSourceApi): boolean { const { type } = datasource; - return type === 'prometheus' || type === 'elasticsearch'; + return type === 'prometheus' || type === 'elasticsearch' || type === 'loki'; } diff --git a/public/app/plugins/datasource/loki/LokiAnnotationsQueryCtrl.tsx b/public/app/plugins/datasource/loki/LokiAnnotationsQueryCtrl.tsx deleted file mode 100644 index 7bc7146ca34..00000000000 --- a/public/app/plugins/datasource/loki/LokiAnnotationsQueryCtrl.tsx +++ /dev/null @@ -1,21 +0,0 @@ -import { LokiQuery } from './types'; -/** - * Just a simple wrapper for a react component that is actually implementing the query editor. - */ -export class LokiAnnotationsQueryCtrl { - static templateUrl = 'partials/annotations.editor.html'; - declare annotation: any; - - /** @ngInject */ - constructor($scope: any) { - this.annotation = $scope.ctrl.annotation; - this.annotation.target = this.annotation.target || {}; - this.onQueryChange = this.onQueryChange.bind(this); - } - - onQueryChange(query: LokiQuery) { - this.annotation.expr = query.expr; - this.annotation.maxLines = query.maxLines; - this.annotation.instant = query.instant; - } -} diff --git a/public/app/plugins/datasource/loki/components/AnnotationsQueryEditor.tsx b/public/app/plugins/datasource/loki/components/AnnotationsQueryEditor.tsx index babf897af12..64c874ec93c 100644 --- a/public/app/plugins/datasource/loki/components/AnnotationsQueryEditor.tsx +++ b/public/app/plugins/datasource/loki/components/AnnotationsQueryEditor.tsx @@ -1,49 +1,126 @@ // Libraries import React, { memo } from 'react'; +import { AnnotationQuery } from '@grafana/data'; +import { EditorRow, EditorField } from '@grafana/experimental'; +import { Input } from '@grafana/ui'; + // Types -import { LokiDatasource } from '../datasource'; -import { LokiQuery } from '../types'; +import { getNormalizedLokiQuery } from '../query_utils'; +import { LokiQuery, LokiQueryType } from '../types'; import { LokiOptionFields } from './LokiOptionFields'; import { LokiQueryField } from './LokiQueryField'; +import { LokiQueryEditorProps } from './types'; -interface Props { - expr: string; - maxLines?: number; - instant?: boolean; - datasource: LokiDatasource; - onChange: (query: LokiQuery) => void; -} +type Props = LokiQueryEditorProps & { + annotation?: AnnotationQuery; + onAnnotationChange?: (annotation: AnnotationQuery) => void; +}; export const LokiAnnotationsQueryEditor = memo(function LokiAnnotationQueryEditor(props: Props) { - const { expr, maxLines, instant, datasource, onChange } = props; + const { annotation, onAnnotationChange } = props; + + // this should never happen, but we want to keep typescript happy + if (annotation === undefined || onAnnotationChange === undefined) { + return null; + } + + const onChangeQuery = (query: LokiQuery) => { + // the current version of annotations only stores an optional boolean + // field `instant` to handle the instant/range switch. + // we need to maintain compatiblity for now, so we do the same. + // we explicitly call `getNormalizedLokiQuery` to make sure `queryType` + // is set up correctly. + const instant = getNormalizedLokiQuery(query).queryType === LokiQueryType.Instant; + onAnnotationChange({ + ...annotation, + expr: query.expr, + maxLines: query.maxLines, + instant, + }); + }; const queryWithRefId: LokiQuery = { refId: '', - expr, - maxLines, - instant, + expr: annotation.expr, + maxLines: annotation.maxLines, + instant: annotation.instant, + queryType: annotation.queryType, }; return ( -
- {}} - onBlur={() => {}} - history={[]} - ExtraFieldElement={ - {}} - onChange={onChange} + <> +
+ {}} + onBlur={() => {}} + history={[]} + ExtraFieldElement={ + {}} + onChange={onChangeQuery} + /> + } + /> +
+ + + + { + onAnnotationChange({ + ...annotation, + titleFormat: event.currentTarget.value, + }); + }} /> - } - /> -
+ + + { + onAnnotationChange({ + ...annotation, + tagKeys: event.currentTarget.value, + }); + }} + /> + + + { + onAnnotationChange({ + ...annotation, + textFormat: event.currentTarget.value, + }); + }} + /> + + + ); }); diff --git a/public/app/plugins/datasource/loki/datasource.ts b/public/app/plugins/datasource/loki/datasource.ts index d7cbe8b8c93..c3e9290a989 100644 --- a/public/app/plugins/datasource/loki/datasource.ts +++ b/public/app/plugins/datasource/loki/datasource.ts @@ -47,6 +47,7 @@ import { renderLegendFormat } from '../prometheus/legend'; import { addLabelToQuery } from './add_label_to_query'; import { transformBackendResult } from './backendResultTransformer'; +import { LokiAnnotationsQueryEditor } from './components/AnnotationsQueryEditor'; import { DEFAULT_RESOLUTION } from './components/LokiOptionFields'; import LanguageProvider from './language_provider'; import { escapeLabelValueInSelector } from './language_utils'; @@ -118,6 +119,9 @@ export class LokiDatasource const settingsData = instanceSettings.jsonData || {}; this.maxLines = parseInt(settingsData.maxLines ?? '0', 10) || DEFAULT_MAX_LINES; this.useBackendMode = config.featureToggles.lokiBackendMode ?? false; + this.annotations = { + QueryEditor: LokiAnnotationsQueryEditor, + }; } _request(apiUrl: string, data?: any, options?: Partial): Observable> { diff --git a/public/app/plugins/datasource/loki/module.ts b/public/app/plugins/datasource/loki/module.ts index 6880f9da640..dddfa023aed 100644 --- a/public/app/plugins/datasource/loki/module.ts +++ b/public/app/plugins/datasource/loki/module.ts @@ -1,6 +1,5 @@ import { DataSourcePlugin } from '@grafana/data'; -import { LokiAnnotationsQueryCtrl } from './LokiAnnotationsQueryCtrl'; import LokiCheatSheet from './components/LokiCheatSheet'; import LokiQueryEditorByApp from './components/LokiQueryEditorByApp'; import { ConfigEditor } from './configuration/ConfigEditor'; @@ -9,5 +8,4 @@ import { LokiDatasource } from './datasource'; export const plugin = new DataSourcePlugin(LokiDatasource) .setQueryEditor(LokiQueryEditorByApp) .setConfigEditor(ConfigEditor) - .setQueryEditorHelp(LokiCheatSheet) - .setAnnotationQueryCtrl(LokiAnnotationsQueryCtrl); + .setQueryEditorHelp(LokiCheatSheet); diff --git a/public/app/plugins/datasource/loki/partials/annotations.editor.html b/public/app/plugins/datasource/loki/partials/annotations.editor.html deleted file mode 100644 index c636dd9d3ba..00000000000 --- a/public/app/plugins/datasource/loki/partials/annotations.editor.html +++ /dev/null @@ -1,28 +0,0 @@ - - - -
-
Field formatsFor title and text fields, use either the name or a pattern. For example, {{instance}} is replaced with label value for the label instance.
-
-
- Title - -
-
- Tags - -
-
-
- Text - -
-
-
-