mirror of https://github.com/grafana/grafana.git
CloudWatch: Fix handling region for legacy alerts (#109217)
This commit is contained in:
parent
295ace108d
commit
2bf9aea8ef
|
@ -382,7 +382,7 @@ func (q *CloudWatchQuery) validateAndSetDefaults(refId string, metricsDataQuery
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if q.Region == defaultRegion {
|
if q.Region == defaultRegion || q.Region == "" {
|
||||||
q.Region = defaultRegionValue
|
q.Region = defaultRegionValue
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1195,7 +1195,7 @@ func Test_ParseMetricDataQueries_account_Id(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func Test_ParseMetricDataQueries_default_region(t *testing.T) {
|
func Test_ParseMetricDataQueries_default_region(t *testing.T) {
|
||||||
t.Run("default region is used when when region not set", func(t *testing.T) {
|
t.Run("default region is used when when region is default", func(t *testing.T) {
|
||||||
query := []backend.DataQuery{
|
query := []backend.DataQuery{
|
||||||
{
|
{
|
||||||
JSON: json.RawMessage(`{
|
JSON: json.RawMessage(`{
|
||||||
|
@ -1216,6 +1216,33 @@ func Test_ParseMetricDataQueries_default_region(t *testing.T) {
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
region := "us-east-2"
|
||||||
|
res, err := ParseMetricDataQueries(query, time.Now().Add(-2*time.Hour), time.Now().Add(-time.Hour), region, logger, false)
|
||||||
|
assert.NoError(t, err)
|
||||||
|
require.Len(t, res, 1)
|
||||||
|
require.NotNil(t, res[0])
|
||||||
|
assert.Equal(t, region, res[0].Region)
|
||||||
|
})
|
||||||
|
t.Run("default region is used when when region not set", func(t *testing.T) {
|
||||||
|
query := []backend.DataQuery{
|
||||||
|
{
|
||||||
|
JSON: json.RawMessage(`{
|
||||||
|
"refId":"ref1",
|
||||||
|
"namespace":"ec2",
|
||||||
|
"metricName":"CPUUtilization",
|
||||||
|
"id": "",
|
||||||
|
"expression": "",
|
||||||
|
"dimensions":{
|
||||||
|
"InstanceId":["test"],
|
||||||
|
"InstanceType":["test2"]
|
||||||
|
},
|
||||||
|
"statistic":"Average",
|
||||||
|
"period":"900",
|
||||||
|
"hide":false
|
||||||
|
}`),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
region := "us-east-2"
|
region := "us-east-2"
|
||||||
res, err := ParseMetricDataQueries(query, time.Now().Add(-2*time.Hour), time.Now().Add(-time.Hour), region, logger, false)
|
res, err := ParseMetricDataQueries(query, time.Now().Add(-2*time.Hour), time.Now().Add(-time.Hour), region, logger, false)
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
|
|
|
@ -4,6 +4,7 @@ import { QueryEditorProps } from '@grafana/data';
|
||||||
|
|
||||||
import { CloudWatchDatasource } from '../../datasource';
|
import { CloudWatchDatasource } from '../../datasource';
|
||||||
import { isCloudWatchLogsQuery, isCloudWatchMetricsQuery } from '../../guards';
|
import { isCloudWatchLogsQuery, isCloudWatchMetricsQuery } from '../../guards';
|
||||||
|
import useMigratedQuery from '../../migrations/useMigratedQuery';
|
||||||
import { CloudWatchJsonData, CloudWatchQuery } from '../../types';
|
import { CloudWatchJsonData, CloudWatchQuery } from '../../types';
|
||||||
|
|
||||||
import LogsQueryEditor from './LogsQueryEditor/LogsQueryEditor';
|
import LogsQueryEditor from './LogsQueryEditor/LogsQueryEditor';
|
||||||
|
@ -14,6 +15,7 @@ export type Props = QueryEditorProps<CloudWatchDatasource, CloudWatchQuery, Clou
|
||||||
|
|
||||||
export const QueryEditor = (props: Props) => {
|
export const QueryEditor = (props: Props) => {
|
||||||
const { query, onChange, data } = props;
|
const { query, onChange, data } = props;
|
||||||
|
const migratedQuery = useMigratedQuery(query, props.onChange);
|
||||||
const [dataIsStale, setDataIsStale] = useState(false);
|
const [dataIsStale, setDataIsStale] = useState(false);
|
||||||
const [extraHeaderElementLeft, setExtraHeaderElementLeft] = useState<JSX.Element>();
|
const [extraHeaderElementLeft, setExtraHeaderElementLeft] = useState<JSX.Element>();
|
||||||
const [extraHeaderElementRight, setExtraHeaderElementRight] = useState<JSX.Element>();
|
const [extraHeaderElementRight, setExtraHeaderElementRight] = useState<JSX.Element>();
|
||||||
|
@ -39,20 +41,20 @@ export const QueryEditor = (props: Props) => {
|
||||||
dataIsStale={dataIsStale}
|
dataIsStale={dataIsStale}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{isCloudWatchMetricsQuery(query) && (
|
{isCloudWatchMetricsQuery(migratedQuery) && (
|
||||||
<MetricsQueryEditor
|
<MetricsQueryEditor
|
||||||
{...props}
|
{...props}
|
||||||
query={query}
|
query={migratedQuery}
|
||||||
onRunQuery={() => {}}
|
onRunQuery={() => {}}
|
||||||
onChange={onChangeInternal}
|
onChange={onChangeInternal}
|
||||||
extraHeaderElementLeft={setExtraHeaderElementLeft}
|
extraHeaderElementLeft={setExtraHeaderElementLeft}
|
||||||
extraHeaderElementRight={setExtraHeaderElementRight}
|
extraHeaderElementRight={setExtraHeaderElementRight}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
{isCloudWatchLogsQuery(query) && (
|
{isCloudWatchLogsQuery(migratedQuery) && (
|
||||||
<LogsQueryEditor
|
<LogsQueryEditor
|
||||||
{...props}
|
{...props}
|
||||||
query={query}
|
query={migratedQuery}
|
||||||
onChange={onChangeInternal}
|
onChange={onChangeInternal}
|
||||||
extraHeaderElementLeft={setExtraHeaderElementLeft}
|
extraHeaderElementLeft={setExtraHeaderElementLeft}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
import { CloudWatchMetricsQuery } from '../types';
|
import { CloudWatchMetricsQuery, MetricEditorMode, MetricQueryType } from '../types';
|
||||||
|
|
||||||
import { migrateAliasPatterns } from './metricQueryMigrations';
|
import { migrateAliasPatterns, migrateMetricQuery } from './metricQueryMigrations';
|
||||||
|
|
||||||
describe('metricQueryMigrations', () => {
|
describe('metricQueryMigrations', () => {
|
||||||
interface TestScenario {
|
interface TestScenario {
|
||||||
|
@ -73,4 +73,23 @@ describe('metricQueryMigrations', () => {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('migrates type and mode', () => {
|
||||||
|
const baseQuery: CloudWatchMetricsQuery = {
|
||||||
|
statistic: 'Average',
|
||||||
|
refId: 'A',
|
||||||
|
id: '',
|
||||||
|
region: 'us-east-2',
|
||||||
|
namespace: 'AWS/EC2',
|
||||||
|
period: '300',
|
||||||
|
alias: '',
|
||||||
|
metricName: 'CPUUtilization',
|
||||||
|
dimensions: {},
|
||||||
|
matchExact: false,
|
||||||
|
expression: '',
|
||||||
|
};
|
||||||
|
const migratedQuery = migrateMetricQuery(baseQuery);
|
||||||
|
expect(migratedQuery.metricQueryType).toBe(MetricQueryType.Search);
|
||||||
|
expect(migratedQuery.metricEditorMode).toBe(MetricEditorMode.Builder);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -2,10 +2,14 @@ import deepEqual from 'fast-deep-equal';
|
||||||
|
|
||||||
import { CloudWatchMetricsQuery } from '../types';
|
import { CloudWatchMetricsQuery } from '../types';
|
||||||
|
|
||||||
|
import { migrateCloudWatchQuery } from './dashboardMigrations';
|
||||||
|
|
||||||
// Call this function to migrate queries from within the plugin.
|
// Call this function to migrate queries from within the plugin.
|
||||||
export function migrateMetricQuery(query: CloudWatchMetricsQuery): CloudWatchMetricsQuery {
|
export function migrateMetricQuery(query: CloudWatchMetricsQuery): CloudWatchMetricsQuery {
|
||||||
|
const newQuery = { ...query };
|
||||||
|
migrateCloudWatchQuery(newQuery);
|
||||||
//add metric query migrations here
|
//add metric query migrations here
|
||||||
const migratedQuery = migrateAliasPatterns(query);
|
const migratedQuery = migrateAliasPatterns(newQuery);
|
||||||
return deepEqual(migratedQuery, query) ? query : migratedQuery;
|
return deepEqual(migratedQuery, query) ? query : migratedQuery;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -11,15 +11,15 @@ const useMigratedMetricsQuery = (
|
||||||
query: CloudWatchMetricsQuery,
|
query: CloudWatchMetricsQuery,
|
||||||
onChangeQuery: (newQuery: CloudWatchMetricsQuery) => void
|
onChangeQuery: (newQuery: CloudWatchMetricsQuery) => void
|
||||||
) => {
|
) => {
|
||||||
const migratedQUery = useMemo(() => migrateMetricQuery(query), [query]);
|
const migratedQuery = useMemo(() => migrateMetricQuery(query), [query]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (migratedQUery !== query) {
|
if (migratedQuery !== query) {
|
||||||
onChangeQuery(migratedQUery);
|
onChangeQuery(migratedQuery);
|
||||||
}
|
}
|
||||||
}, [migratedQUery, query, onChangeQuery]);
|
}, [migratedQuery, query, onChangeQuery]);
|
||||||
|
|
||||||
return migratedQUery;
|
return migratedQuery;
|
||||||
};
|
};
|
||||||
|
|
||||||
export default useMigratedMetricsQuery;
|
export default useMigratedMetricsQuery;
|
||||||
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
import { migrateQuery } from './useMigratedQuery';
|
||||||
|
|
||||||
|
describe('useMigratedQuery', () => {
|
||||||
|
it('adds region and queryMode', () => {
|
||||||
|
const legacyQuery = {
|
||||||
|
statistic: 'Average',
|
||||||
|
refId: 'A',
|
||||||
|
id: '',
|
||||||
|
region: '',
|
||||||
|
namespace: 'AWS/EC2',
|
||||||
|
period: '300',
|
||||||
|
alias: '',
|
||||||
|
metricName: 'CPUUtilization',
|
||||||
|
dimensions: {},
|
||||||
|
matchExact: false,
|
||||||
|
expression: '',
|
||||||
|
};
|
||||||
|
const migratedQuery = migrateQuery(legacyQuery);
|
||||||
|
expect(migratedQuery.region).toBe('default');
|
||||||
|
expect(migratedQuery.queryMode).toBe('Metrics');
|
||||||
|
});
|
||||||
|
});
|
|
@ -0,0 +1,33 @@
|
||||||
|
import deepEqual from 'fast-deep-equal';
|
||||||
|
import { useEffect, useMemo } from 'react';
|
||||||
|
|
||||||
|
import { CloudWatchQuery } from '../types';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns queries with migrations, and calls onChange function to notify if it changes
|
||||||
|
*/
|
||||||
|
const useMigratedQuery = (query: CloudWatchQuery, onChangeQuery: (newQuery: CloudWatchQuery) => void) => {
|
||||||
|
const migratedQuery = useMemo(() => migrateQuery(query), [query]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (migratedQuery !== query) {
|
||||||
|
onChangeQuery(migratedQuery);
|
||||||
|
}
|
||||||
|
}, [migratedQuery, query, onChangeQuery]);
|
||||||
|
|
||||||
|
return migratedQuery;
|
||||||
|
};
|
||||||
|
|
||||||
|
// The frontend doesn't run legacy queries if we don't set the queryMode and region
|
||||||
|
export function migrateQuery(query: CloudWatchQuery): CloudWatchQuery {
|
||||||
|
const newQuery = { ...query };
|
||||||
|
if (!newQuery.queryMode) {
|
||||||
|
newQuery.queryMode = 'Metrics';
|
||||||
|
}
|
||||||
|
if (!newQuery.region) {
|
||||||
|
newQuery.region = 'default';
|
||||||
|
}
|
||||||
|
return deepEqual(newQuery, query) ? query : newQuery;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default useMigratedQuery;
|
Loading…
Reference in New Issue