From 08727b7d6cb6200432f6f8fb2ce06c5db12e7410 Mon Sep 17 00:00:00 2001 From: ismail simsek Date: Wed, 12 Apr 2023 17:22:35 +0200 Subject: [PATCH] Prometheus: Show initial hint on builder mode when metric lookup disabled (#65827) * Show initial hint on builder mode when metric lookup disabled * Disable MetricEncyclopedia and label request when metric lookup is disabled --- lerna.json | 4 +- .../public_dashboard_store_mock.go | 2 +- .../components/MetricSelect.test.tsx | 5 ++- .../querybuilder/components/MetricSelect.tsx | 22 ++++++++-- .../components/PromQueryBuilder.test.tsx | 40 +++++++++++++++++++ .../components/PromQueryBuilder.tsx | 19 ++++++++- 6 files changed, 80 insertions(+), 12 deletions(-) diff --git a/lerna.json b/lerna.json index 75716a4cd76..ffc0d55874a 100644 --- a/lerna.json +++ b/lerna.json @@ -1,8 +1,6 @@ { "npmClient": "yarn", "useWorkspaces": true, - "packages": [ - "packages/*" - ], + "packages": ["packages/*"], "version": "10.0.0-pre" } diff --git a/pkg/services/publicdashboards/public_dashboard_store_mock.go b/pkg/services/publicdashboards/public_dashboard_store_mock.go index 47fccf70101..564a6cf755a 100644 --- a/pkg/services/publicdashboards/public_dashboard_store_mock.go +++ b/pkg/services/publicdashboards/public_dashboard_store_mock.go @@ -6,8 +6,8 @@ import ( context "context" dashboards "github.com/grafana/grafana/pkg/services/dashboards" - mock "github.com/stretchr/testify/mock" models "github.com/grafana/grafana/pkg/services/publicdashboards/models" + mock "github.com/stretchr/testify/mock" ) // FakePublicDashboardStore is an autogenerated mock type for the Store type diff --git a/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.test.tsx b/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.test.tsx index e76a6fecc54..63344ad82e5 100644 --- a/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.test.tsx +++ b/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.test.tsx @@ -7,7 +7,7 @@ import { DataSourceInstanceSettings, MetricFindValue } from '@grafana/data/src'; import { PrometheusDatasource } from '../../datasource'; import { PromOptions } from '../../types'; -import { MetricSelect } from './MetricSelect'; +import { MetricSelect, Props } from './MetricSelect'; const instanceSettings = { url: 'proxied', @@ -44,7 +44,7 @@ dataSourceMock.metricFindQuery = jest.fn((query: string) => { ); }); -const props = { +const props: Props = { labelsFilters: [], datasource: dataSourceMock, query: { @@ -54,6 +54,7 @@ const props = { }, onChange: jest.fn(), onGetMetrics: jest.fn().mockResolvedValue(mockValues), + metricLookupDisabled: false, }; describe('MetricSelect', () => { diff --git a/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.tsx b/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.tsx index ced806d0c77..74c48ef49cc 100644 --- a/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.tsx +++ b/public/app/plugins/datasource/prometheus/querybuilder/components/MetricSelect.tsx @@ -3,7 +3,7 @@ import debounce from 'debounce-promise'; import React, { useCallback, useState } from 'react'; import Highlighter from 'react-highlight-words'; -import { SelectableValue, toOption, GrafanaTheme2 } from '@grafana/data'; +import { GrafanaTheme2, SelectableValue, toOption } from '@grafana/data'; import { EditorField, EditorFieldGroup } from '@grafana/experimental'; import { AsyncSelect, FormatOptionLabelMeta, useStyles2 } from '@grafana/ui'; @@ -16,6 +16,7 @@ import { PromVisualQuery } from '../types'; const splitSeparator = ' '; export interface Props { + metricLookupDisabled: boolean; query: PromVisualQuery; onChange: (query: PromVisualQuery) => void; onGetMetrics: () => Promise; @@ -25,7 +26,14 @@ export interface Props { export const PROMETHEUS_QUERY_BUILDER_MAX_RESULTS = 1000; -export function MetricSelect({ datasource, query, onChange, onGetMetrics, labelsFilters }: Props) { +export function MetricSelect({ + datasource, + query, + onChange, + onGetMetrics, + labelsFilters, + metricLookupDisabled, +}: Props) { const styles = useStyles2(getStyles); const [state, setState] = useState<{ metrics?: Array>; @@ -114,6 +122,9 @@ export function MetricSelect({ datasource, query, onChange, onGetMetrics, labels }); }; + // When metric and label lookup is disabled we won't request labels + const metricLookupDisabledSearch = () => Promise.resolve([]); + const debouncedSearch = debounce( (query: string) => getMetricLabels(query), datasource.getDebounceTimeInMilliseconds() @@ -126,11 +137,14 @@ export function MetricSelect({ datasource, query, onChange, onGetMetrics, labels inputId="prometheus-metric-select" className={styles.select} value={query.metric ? toOption(query.metric) : undefined} - placeholder="Select metric" + placeholder={'Select metric'} allowCustomValue formatOptionLabel={formatOptionLabel} filterOption={customFilterOption} onOpenMenu={async () => { + if (metricLookupDisabled) { + return; + } setState({ isLoading: true }); const metrics = await onGetMetrics(); if (metrics.length > PROMETHEUS_QUERY_BUILDER_MAX_RESULTS) { @@ -138,7 +152,7 @@ export function MetricSelect({ datasource, query, onChange, onGetMetrics, labels } setState({ metrics, isLoading: undefined }); }} - loadOptions={debouncedSearch} + loadOptions={metricLookupDisabled ? metricLookupDisabledSearch : debouncedSearch} isLoading={state.isLoading} defaultOptions={state.metrics} onChange={({ value }) => { diff --git a/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.test.tsx b/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.test.tsx index 493495c3f72..7a04f3224dc 100644 --- a/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.test.tsx +++ b/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.test.tsx @@ -8,6 +8,7 @@ import { LoadingState, MutableDataFrame, PanelData, + QueryHint, TimeRange, } from '@grafana/data'; @@ -229,6 +230,45 @@ describe('PromQueryBuilder', () => { expect(await screen.queryByText(EXPLAIN_LABEL_FILTER_CONTENT)).not.toBeInTheDocument(); }); + it('renders hint if initial hint provided', async () => { + const { datasource } = createDatasource(); + datasource.getInitHints = (): QueryHint[] => [ + { + label: 'Initial hint', + type: 'warning', + }, + ]; + const props = createProps(datasource); + render( + + ); + expect(await screen.queryByText('Initial hint')).toBeInTheDocument(); + }); + + it('renders no hint if no initial hint provided', async () => { + const { datasource } = createDatasource(); + datasource.getInitHints = (): QueryHint[] => []; + const props = createProps(datasource); + render( + + ); + expect(await screen.queryByText('Initial hint')).not.toBeInTheDocument(); + }); + // it('tries to load labels when metric selected modern prom', async () => { const { languageProvider } = setup(undefined, undefined, { diff --git a/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.tsx b/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.tsx index 894f9d97298..d56c50722da 100644 --- a/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.tsx +++ b/public/app/plugins/datasource/prometheus/querybuilder/components/PromQueryBuilder.tsx @@ -208,12 +208,14 @@ export const PromQueryBuilder = React.memo((props) => { }, [datasource, query, withTemplateVariableOptions]); const lang = { grammar: promqlGrammar, name: 'promql' }; - const MetricEncyclopedia = config.featureToggles.prometheusMetricEncyclopedia; + const isMetricEncyclopediaEnabled = config.featureToggles.prometheusMetricEncyclopedia; + + const initHints = datasource.getInitHints(); return ( <> - {MetricEncyclopedia ? ( + {isMetricEncyclopediaEnabled && !datasource.lookupsDisabled ? ( <> + ) : null} + + + ) : null} {showExplain && (