diff --git a/.betterer.results b/.betterer.results index e3fcac92f67..3ddad488ca5 100644 --- a/.betterer.results +++ b/.betterer.results @@ -5364,9 +5364,6 @@ exports[`better eslint`] = { [0, 0, 0, "Unexpected any. Specify a different type.", "0"], [0, 0, 0, "Unexpected any. Specify a different type.", "1"] ], - "public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.test.ts:5381": [ - [0, 0, 0, "Unexpected any. Specify a different type.", "0"] - ], "public/app/plugins/datasource/cloudwatch/components/PanelQueryEditor.test.tsx:5381": [ [0, 0, 0, "Unexpected any. Specify a different type.", "0"], [0, 0, 0, "Unexpected any. Specify a different type.", "1"], diff --git a/public/app/plugins/datasource/cloudwatch/__mocks__/CloudWatchDataSource.ts b/public/app/plugins/datasource/cloudwatch/__mocks__/CloudWatchDataSource.ts index 192561b8e1b..a108422b18c 100644 --- a/public/app/plugins/datasource/cloudwatch/__mocks__/CloudWatchDataSource.ts +++ b/public/app/plugins/datasource/cloudwatch/__mocks__/CloudWatchDataSource.ts @@ -62,10 +62,12 @@ export function setupMockedDataSource({ variables, mockGetVariableName = true, getMock = jest.fn(), + customInstanceSettings = CloudWatchSettings, }: { getMock?: jest.Func; variables?: CustomVariableModel[]; mockGetVariableName?: boolean; + customInstanceSettings?: DataSourceInstanceSettings; } = {}) { let templateService = new TemplateSrv(); if (variables) { @@ -76,7 +78,7 @@ export function setupMockedDataSource({ } const timeSrv = getTimeSrv(); - const datasource = new CloudWatchDatasource(CloudWatchSettings, templateService, timeSrv); + const datasource = new CloudWatchDatasource(customInstanceSettings, templateService, timeSrv); datasource.getVariables = () => ['test']; datasource.api.describeLogGroups = jest.fn().mockResolvedValue([]); datasource.api.getNamespaces = jest.fn().mockResolvedValue([]); diff --git a/public/app/plugins/datasource/cloudwatch/components/LogsQueryField.tsx b/public/app/plugins/datasource/cloudwatch/components/LogsQueryField.tsx index 487345359e2..1fcc8b456ad 100644 --- a/public/app/plugins/datasource/cloudwatch/components/LogsQueryField.tsx +++ b/public/app/plugins/datasource/cloudwatch/components/LogsQueryField.tsx @@ -75,14 +75,6 @@ class CloudWatchLogsQueryField extends React.PureComponent { - const { query, datasource, onChange } = this.props; - - if (onChange) { - onChange({ ...query, logGroupNames: query.logGroupNames ?? datasource.logsQueryRunner.defaultLogGroups }); - } - }; - onChangeQuery = (value: string) => { // Send text change to parent const { query, onChange } = this.props; diff --git a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/MetricsQueryEditor.tsx b/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/MetricsQueryEditor.tsx index 7b8b1e39149..0a389fd6484 100644 --- a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/MetricsQueryEditor.tsx +++ b/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/MetricsQueryEditor.tsx @@ -8,6 +8,7 @@ import { Input } from '@grafana/ui'; import { MathExpressionQueryField, MetricStatEditor, SQLBuilderEditor, SQLCodeEditor } from '../'; import { CloudWatchDatasource } from '../../datasource'; import { isCloudWatchMetricsQuery } from '../../guards'; +import useMigratedMetricsQuery from '../../migrations/useMigratedMetricsQuery'; import { CloudWatchJsonData, CloudWatchMetricsQuery, @@ -20,7 +21,6 @@ import { DynamicLabelsField } from '../DynamicLabelsField'; import QueryHeader from '../QueryHeader'; import { Alias } from './Alias'; -import usePreparedMetricsQuery from './usePreparedMetricsQuery'; export interface Props extends QueryEditorProps { query: CloudWatchMetricsQuery; @@ -29,7 +29,7 @@ export interface Props extends QueryEditorProps { const { query, onRunQuery, datasource } = props; const [sqlCodeEditorIsDirty, setSQLCodeEditorIsDirty] = useState(false); - const preparedQuery = usePreparedMetricsQuery(query, props.onChange); + const migratedQuery = useMigratedMetricsQuery(query, props.onChange); const onChange = (query: CloudWatchQuery) => { const { onChange, onRunQuery } = props; @@ -83,7 +83,7 @@ export const MetricsQueryEditor = (props: Props) => { if (!sqlCodeEditorIsDirty) { setSQLCodeEditorIsDirty(true); } - props.onChange({ ...preparedQuery, sqlExpression }); + props.onChange({ ...migratedQuery, sqlExpression }); }} onRunQuery={onRunQuery} datasource={datasource} @@ -114,7 +114,7 @@ export const MetricsQueryEditor = (props: Props) => { ) => onChange({ ...preparedQuery, id: event.target.value })} + onChange={(event: ChangeEvent) => onChange({ ...migratedQuery, id: event.target.value })} type="text" value={query.id} /> @@ -127,7 +127,7 @@ export const MetricsQueryEditor = (props: Props) => { placeholder="auto" onBlur={onRunQuery} onChange={(event: ChangeEvent) => - onChange({ ...preparedQuery, period: event.target.value }) + onChange({ ...migratedQuery, period: event.target.value }) } /> @@ -142,7 +142,7 @@ export const MetricsQueryEditor = (props: Props) => { props.onChange({ ...query, label })} > @@ -155,8 +155,8 @@ export const MetricsQueryEditor = (props: Props) => { > onChange({ ...preparedQuery, alias: value })} + value={migratedQuery.alias ?? ''} + onChange={(value: string) => onChange({ ...migratedQuery, alias: value })} /> )} diff --git a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.test.ts b/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.test.ts deleted file mode 100644 index 45bfb80d0e8..00000000000 --- a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.test.ts +++ /dev/null @@ -1,76 +0,0 @@ -import { renderHook } from '@testing-library/react-hooks'; - -import { CloudWatchMetricsQuery, MetricEditorMode, MetricQueryType } from '../../types'; - -import usePreparedMetricsQuery, { DEFAULT_QUERY } from './usePreparedMetricsQuery'; - -interface TestScenario { - name: string; - query: any; - expectedQuery: CloudWatchMetricsQuery; -} - -const baseQuery: CloudWatchMetricsQuery = { - refId: 'A', - id: '', - region: 'us-east-2', - namespace: 'AWS/EC2', - dimensions: { InstanceId: 'x-123' }, -}; - -describe('usePrepareMetricsQuery', () => { - describe('when an incomplete query is provided', () => { - const testTable: TestScenario[] = [ - { name: 'Empty query', query: { refId: 'A' }, expectedQuery: { ...DEFAULT_QUERY, refId: 'A' } }, - { - name: 'Match exact is not part of the query', - query: { ...baseQuery }, - expectedQuery: { ...DEFAULT_QUERY, ...baseQuery, matchExact: true }, - }, - { - name: 'Match exact is part of the query', - query: { ...baseQuery, matchExact: false }, - expectedQuery: { ...DEFAULT_QUERY, ...baseQuery, matchExact: false }, - }, - { - name: 'When editor mode and builder mode different from default is specified', - query: { ...baseQuery, metricQueryType: MetricQueryType.Query, metricEditorMode: MetricEditorMode.Code }, - expectedQuery: { - ...DEFAULT_QUERY, - ...baseQuery, - metricQueryType: MetricQueryType.Query, - metricEditorMode: MetricEditorMode.Code, - }, - }, - ]; - describe.each(testTable)('scenario %#: $name', (scenario) => { - it('should set the default values and trigger onChangeQuery', async () => { - const onChangeQuery = jest.fn(); - const { result } = renderHook(() => usePreparedMetricsQuery(scenario.query, onChangeQuery)); - expect(onChangeQuery).toHaveBeenLastCalledWith(result.current); - expect(result.current).toEqual(scenario.expectedQuery); - }); - }); - }); - - describe('when a complete query is provided', () => { - it('should not change the query and should not call onChangeQuery', async () => { - const onChangeQuery = jest.fn(); - const completeQuery: CloudWatchMetricsQuery = { - ...baseQuery, - expression: '', - queryMode: 'Metrics', - metricName: '', - statistic: 'Sum', - period: '300', - metricQueryType: MetricQueryType.Query, - metricEditorMode: MetricEditorMode.Code, - sqlExpression: 'SELECT 1', - matchExact: false, - }; - const { result } = renderHook(() => usePreparedMetricsQuery(completeQuery, onChangeQuery)); - expect(onChangeQuery).not.toHaveBeenCalled(); - expect(result.current).toEqual(completeQuery); - }); - }); -}); diff --git a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.ts b/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.ts deleted file mode 100644 index 0e0f618fcc1..00000000000 --- a/public/app/plugins/datasource/cloudwatch/components/MetricsQueryEditor/usePreparedMetricsQuery.ts +++ /dev/null @@ -1,50 +0,0 @@ -import deepEqual from 'fast-deep-equal'; -import { useEffect, useMemo } from 'react'; - -import { migrateMetricQuery } from '../../migrations/metricQueryMigrations'; -import { CloudWatchMetricsQuery, MetricEditorMode, MetricQueryType } from '../../types'; - -export const DEFAULT_QUERY: Omit = { - queryMode: 'Metrics', - namespace: '', - metricName: '', - expression: '', - dimensions: {}, - region: 'default', - id: '', - statistic: 'Average', - period: '', - metricQueryType: MetricQueryType.Search, - metricEditorMode: MetricEditorMode.Builder, - sqlExpression: '', - matchExact: true, -}; - -const prepareQuery = (query: CloudWatchMetricsQuery) => { - const withDefaults = { ...DEFAULT_QUERY, ...query }; - const migratedQuery = migrateMetricQuery(withDefaults); - - // If we didn't make any changes to the object, then return the original object to keep the - // identity the same, and not trigger any other useEffects or anything. - return deepEqual(migratedQuery, query) ? query : migratedQuery; -}; - -/** - * Returns queries with some defaults + migrations, and calls onChange function to notify if it changes - */ -const usePreparedMetricsQuery = ( - query: CloudWatchMetricsQuery, - onChangeQuery: (newQuery: CloudWatchMetricsQuery) => void -) => { - const preparedQuery = useMemo(() => prepareQuery(query), [query]); - - useEffect(() => { - if (preparedQuery !== query) { - onChangeQuery(preparedQuery); - } - }, [preparedQuery, query, onChangeQuery]); - - return preparedQuery; -}; - -export default usePreparedMetricsQuery; diff --git a/public/app/plugins/datasource/cloudwatch/components/QueryHeader.tsx b/public/app/plugins/datasource/cloudwatch/components/QueryHeader.tsx index 5d302f5b083..53529f92521 100644 --- a/public/app/plugins/datasource/cloudwatch/components/QueryHeader.tsx +++ b/public/app/plugins/datasource/cloudwatch/components/QueryHeader.tsx @@ -1,4 +1,3 @@ -import { pick } from 'lodash'; import React from 'react'; import { SelectableValue, ExploreMode } from '@grafana/data'; @@ -34,9 +33,8 @@ const QueryHeader: React.FC = ({ query, sqlCodeEditorIsDirty, const onQueryModeChange = ({ value }: SelectableValue) => { if (value !== queryMode) { - const commonProps = pick(query, 'id', 'region', 'namespace', 'refId', 'hide', 'key', 'queryType', 'datasource'); onChange({ - ...commonProps, + ...query, queryMode: value, } as CloudWatchQuery); } diff --git a/public/app/plugins/datasource/cloudwatch/datasource.test.ts b/public/app/plugins/datasource/cloudwatch/datasource.test.ts index 545525d1b9c..2be3be9381b 100644 --- a/public/app/plugins/datasource/cloudwatch/datasource.test.ts +++ b/public/app/plugins/datasource/cloudwatch/datasource.test.ts @@ -1,9 +1,10 @@ import { lastValueFrom } from 'rxjs'; import { toArray } from 'rxjs/operators'; -import { dateTime, Field } from '@grafana/data'; +import { CoreApp, dateTime, Field } from '@grafana/data'; import { + CloudWatchSettings, fieldsVariable, logGroupNamesVariable, regionVariable, @@ -12,7 +13,14 @@ import { import { setupForLogs } from './__mocks__/logsTestContext'; import { validLogsQuery, validMetricSearchBuilderQuery } from './__mocks__/queries'; import { TimeRangeMock } from './__mocks__/timeRange'; -import { CloudWatchLogsQuery, CloudWatchMetricsQuery, CloudWatchQuery } from './types'; +import { + CloudWatchLogsQuery, + CloudWatchMetricsQuery, + CloudWatchQuery, + CloudWatchDefaultQuery, + MetricEditorMode, + MetricQueryType, +} from './types'; describe('datasource', () => { beforeEach(() => { @@ -338,4 +346,34 @@ describe('datasource', () => { expect(templateService.getVariableName).toHaveBeenCalledTimes(1); }); }); + + describe('when setting default query', () => { + it('should set default query to be a Metrics query', () => { + const { datasource } = setupMockedDataSource(); + expect(datasource.getDefaultQuery(CoreApp.PanelEditor).queryMode).toEqual('Metrics'); + }); + it('should set default log groups in default query', () => { + const { datasource } = setupMockedDataSource({ + customInstanceSettings: { + ...CloudWatchSettings, + jsonData: { ...CloudWatchSettings.jsonData, defaultLogGroups: ['testLogGroup'] }, + }, + }); + expect((datasource.getDefaultQuery(CoreApp.PanelEditor) as CloudWatchDefaultQuery).logGroupNames).toEqual([ + 'testLogGroup', + ]); + }); + it('should set default values from metrics query', () => { + const { datasource } = setupMockedDataSource(); + expect(datasource.getDefaultQuery(CoreApp.PanelEditor).region).toEqual('default'); + expect((datasource.getDefaultQuery(CoreApp.PanelEditor) as CloudWatchDefaultQuery).statistic).toEqual('Average'); + expect((datasource.getDefaultQuery(CoreApp.PanelEditor) as CloudWatchDefaultQuery).metricQueryType).toEqual( + MetricQueryType.Search + ); + expect((datasource.getDefaultQuery(CoreApp.PanelEditor) as CloudWatchDefaultQuery).metricEditorMode).toEqual( + MetricEditorMode.Builder + ); + expect((datasource.getDefaultQuery(CoreApp.PanelEditor) as CloudWatchDefaultQuery).matchExact).toEqual(true); + }); + }); }); diff --git a/public/app/plugins/datasource/cloudwatch/datasource.ts b/public/app/plugins/datasource/cloudwatch/datasource.ts index 1d354da4311..5e6cab8bd84 100644 --- a/public/app/plugins/datasource/cloudwatch/datasource.ts +++ b/public/app/plugins/datasource/cloudwatch/datasource.ts @@ -2,6 +2,7 @@ import { cloneDeep, find, isEmpty } from 'lodash'; import { merge, Observable, of } from 'rxjs'; import { + CoreApp, DataFrame, DataQueryRequest, DataQueryResponse, @@ -20,6 +21,7 @@ import { RowContextOptions } from '../../../features/logs/components/LogRowConte import { CloudWatchAnnotationSupport } from './annotationSupport'; import { CloudWatchAPI } from './api'; import { SQLCompletionItemProvider } from './cloudwatch-sql/completion/CompletionItemProvider'; +import { DEFAULT_METRICS_QUERY, getDefaultLogsQuery } from './defaultQueries'; import { isCloudWatchAnnotationQuery, isCloudWatchLogsQuery, isCloudWatchMetricsQuery } from './guards'; import { CloudWatchLanguageProvider } from './language_provider'; import { MetricMathCompletionItemProvider } from './metric-math/completion/CompletionItemProvider'; @@ -43,6 +45,7 @@ export class CloudWatchDatasource languageProvider: CloudWatchLanguageProvider; sqlCompletionItemProvider: SQLCompletionItemProvider; metricMathCompletionItemProvider: MetricMathCompletionItemProvider; + defaultLogGroups?: string[]; type = 'cloudwatch'; @@ -67,6 +70,7 @@ export class CloudWatchDatasource this.annotationQueryRunner = new CloudWatchAnnotationQueryRunner(instanceSettings, templateSrv); this.variables = new CloudWatchVariableSupport(this.api); this.annotations = CloudWatchAnnotationSupport; + this.defaultLogGroups = instanceSettings.jsonData.defaultLogGroups; } filterQuery(query: CloudWatchQuery) { @@ -173,4 +177,11 @@ export class CloudWatchDatasource } return region; } + + getDefaultQuery(_: CoreApp): Partial { + return { + ...getDefaultLogsQuery(this.defaultLogGroups), + ...DEFAULT_METRICS_QUERY, + }; + } } diff --git a/public/app/plugins/datasource/cloudwatch/defaultQueries.ts b/public/app/plugins/datasource/cloudwatch/defaultQueries.ts new file mode 100644 index 00000000000..42eaf74fa8a --- /dev/null +++ b/public/app/plugins/datasource/cloudwatch/defaultQueries.ts @@ -0,0 +1,24 @@ +import { CloudWatchLogsQuery, CloudWatchMetricsQuery, MetricEditorMode, MetricQueryType } from './types'; + +export const DEFAULT_METRICS_QUERY: Omit = { + queryMode: 'Metrics', + namespace: '', + metricName: '', + expression: '', + dimensions: {}, + region: 'default', + id: '', + statistic: 'Average', + period: '', + metricQueryType: MetricQueryType.Search, + metricEditorMode: MetricEditorMode.Builder, + sqlExpression: '', + matchExact: true, +}; + +export const getDefaultLogsQuery = (defaultLogGroups?: string[]): Omit => ({ + id: '', + region: 'default', + expression: '', + logGroupNames: defaultLogGroups, +}); diff --git a/public/app/plugins/datasource/cloudwatch/migrations/metricQueryMigrations.ts b/public/app/plugins/datasource/cloudwatch/migrations/metricQueryMigrations.ts index 446b44c7710..0cffd1cdb6e 100644 --- a/public/app/plugins/datasource/cloudwatch/migrations/metricQueryMigrations.ts +++ b/public/app/plugins/datasource/cloudwatch/migrations/metricQueryMigrations.ts @@ -1,3 +1,5 @@ +import deepEqual from 'fast-deep-equal'; + import { config } from '@grafana/runtime'; import { CloudWatchMetricsQuery } from '../types'; @@ -6,7 +8,7 @@ import { CloudWatchMetricsQuery } from '../types'; export function migrateMetricQuery(query: CloudWatchMetricsQuery): CloudWatchMetricsQuery { //add metric query migrations here const migratedQuery = migrateAliasPatterns(query); - return migratedQuery; + return deepEqual(migratedQuery, query) ? query : migratedQuery; } const aliasPatterns: Record = { @@ -20,16 +22,19 @@ const aliasPatterns: Record = { export function migrateAliasPatterns(query: CloudWatchMetricsQuery): CloudWatchMetricsQuery { if (config.featureToggles.cloudWatchDynamicLabels && !query.hasOwnProperty('label')) { - const regex = /{{\s*(.+?)\s*}}/g; - query.label = - query.alias?.replace(regex, (_, value) => { - if (aliasPatterns.hasOwnProperty(value)) { - return `\${${aliasPatterns[value]}}`; - } + const newQuery = { ...query }; + if (!query.hasOwnProperty('label')) { + const regex = /{{\s*(.+?)\s*}}/g; + newQuery.label = + query.alias?.replace(regex, (_, value) => { + if (aliasPatterns.hasOwnProperty(value)) { + return `\${${aliasPatterns[value]}}`; + } - return `\${PROP('Dim.${value}')}`; - }) ?? ''; + return `\${PROP('Dim.${value}')}`; + }) ?? ''; + } + return newQuery; } - return query; } diff --git a/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.test.ts b/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.test.ts new file mode 100644 index 00000000000..8b1ac99a964 --- /dev/null +++ b/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.test.ts @@ -0,0 +1,44 @@ +import { renderHook } from '@testing-library/react-hooks'; + +import { config } from '@grafana/runtime'; + +import { DEFAULT_METRICS_QUERY } from '../defaultQueries'; +import { CloudWatchMetricsQuery } from '../types'; + +import { migrateAliasPatterns } from './metricQueryMigrations'; +import useMigratedMetricsQuery from './useMigratedMetricsQuery'; + +describe('usePrepareMetricsQuery', () => { + const DEFAULT_TEST_QUERY: CloudWatchMetricsQuery = { ...DEFAULT_METRICS_QUERY, refId: 'testId' }; + describe('when dynamic labels are true and there is no label', () => { + const testQuery: CloudWatchMetricsQuery = { ...DEFAULT_TEST_QUERY, alias: 'test' }; + it('should replace label with alias and trigger onChangeQuery', async () => { + config.featureToggles.cloudWatchDynamicLabels = true; + const expectedQuery: CloudWatchMetricsQuery = migrateAliasPatterns(testQuery); + const onChangeQuery = jest.fn(); + const { result } = renderHook(() => useMigratedMetricsQuery(testQuery, onChangeQuery)); + expect(onChangeQuery).toHaveBeenLastCalledWith(result.current); + expect(result.current).toEqual(expectedQuery); + }); + }); + describe('when query has a label', () => { + config.featureToggles.cloudWatchDynamicLabels = true; + const testQuery: CloudWatchMetricsQuery = { ...DEFAULT_TEST_QUERY, label: 'test' }; + it('should not replace label or trigger onChange', async () => { + const onChangeQuery = jest.fn(); + const { result } = renderHook(() => useMigratedMetricsQuery(testQuery, onChangeQuery)); + expect(result.current).toEqual(testQuery); + expect(onChangeQuery).toHaveBeenCalledTimes(0); + }); + }); + describe('when dynamic labels feature flag is disabled', () => { + const testQuery: CloudWatchMetricsQuery = { ...DEFAULT_TEST_QUERY }; + it('should not replace label or trigger onChange', async () => { + config.featureToggles.cloudWatchDynamicLabels = false; + const onChangeQuery = jest.fn(); + const { result } = renderHook(() => useMigratedMetricsQuery(testQuery, onChangeQuery)); + expect(result.current).toEqual(testQuery); + expect(onChangeQuery).toHaveBeenCalledTimes(0); + }); + }); +}); diff --git a/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.ts b/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.ts new file mode 100644 index 00000000000..fcfb9955770 --- /dev/null +++ b/public/app/plugins/datasource/cloudwatch/migrations/useMigratedMetricsQuery.ts @@ -0,0 +1,25 @@ +import { useEffect, useMemo } from 'react'; + +import { CloudWatchMetricsQuery } from '../types'; + +import { migrateMetricQuery } from './metricQueryMigrations'; + +/** + * Returns queries with migrations, and calls onChange function to notify if it changes + */ +const useMigratedMetricsQuery = ( + query: CloudWatchMetricsQuery, + onChangeQuery: (newQuery: CloudWatchMetricsQuery) => void +) => { + const migratedQUery = useMemo(() => migrateMetricQuery(query), [query]); + + useEffect(() => { + if (migratedQUery !== query) { + onChangeQuery(migratedQUery); + } + }, [migratedQUery, query, onChangeQuery]); + + return migratedQUery; +}; + +export default useMigratedMetricsQuery; diff --git a/public/app/plugins/datasource/cloudwatch/types.ts b/public/app/plugins/datasource/cloudwatch/types.ts index 3f17b651ead..daee72448b3 100644 --- a/public/app/plugins/datasource/cloudwatch/types.ts +++ b/public/app/plugins/datasource/cloudwatch/types.ts @@ -105,8 +105,14 @@ export interface CloudWatchLogsQuery extends DataQuery { /* not quite deprecated yet, but will be soon */ logGroupNames?: string[]; } +// We want to allow setting defaults for both Logs and Metrics queries +export type CloudWatchDefaultQuery = Omit & CloudWatchMetricsQuery; -export type CloudWatchQuery = CloudWatchMetricsQuery | CloudWatchLogsQuery | CloudWatchAnnotationQuery; +export type CloudWatchQuery = + | CloudWatchMetricsQuery + | CloudWatchLogsQuery + | CloudWatchAnnotationQuery + | CloudWatchDefaultQuery; export interface CloudWatchAnnotationQuery extends MetricStat, DataQuery { queryMode: 'Annotations';