From 2baf967ff10c75e51084210a5865fd6858df4831 Mon Sep 17 00:00:00 2001 From: Andriy Date: Fri, 13 Jan 2023 10:37:29 +0100 Subject: [PATCH] fix: Fix flattening queries with `null` values (#61380) --- .../features/variables/query/actions.test.tsx | 89 +++++++++++++++++++ .../app/features/variables/query/actions.ts | 4 +- 2 files changed, 91 insertions(+), 2 deletions(-) diff --git a/public/app/features/variables/query/actions.test.tsx b/public/app/features/variables/query/actions.test.tsx index 028efcc7431..30e55a0faca 100644 --- a/public/app/features/variables/query/actions.test.tsx +++ b/public/app/features/variables/query/actions.test.tsx @@ -713,6 +713,95 @@ describe('query actions', () => { }); }); }); + + it('returns correct result when called with an object with null values inside', () => { + const query = { + level2: { + level3: { + query: '${query3}', + refId: 'C', + num: 2, + bool: true, + null: null, + arr: [ + { query: '${query4}', refId: 'D', num: 4, bool: true }, + { + query: '${query5}', + refId: 'E', + num: 5, + bool: true, + arr: [{ query: '${query6}', refId: 'F', num: 6, bool: true }], + }, + ], + }, + query: '${query2}', + refId: 'B', + num: 1, + bool: false, + }, + query: '${query1}', + refId: 'A', + num: 0, + bool: true, + arr: [ + { query: '${query7}', refId: 'G', num: 7, bool: true }, + { + query: '${query8}', + refId: 'H', + num: 8, + bool: true, + arr: [{ query: '${query9}', refId: 'I', num: 9, bool: true, null: null }], + }, + ], + }; + + expect(flattenQuery(query)).toEqual({ + query: '${query1}', + refId: 'A', + num: 0, + bool: true, + level2_query: '${query2}', + level2_refId: 'B', + level2_num: 1, + level2_bool: false, + level2_level3_query: '${query3}', + level2_level3_refId: 'C', + level2_level3_num: 2, + level2_level3_bool: true, + level2_level3_null: null, + level2_level3_arr_0_query: '${query4}', + level2_level3_arr_0_refId: 'D', + level2_level3_arr_0_num: 4, + level2_level3_arr_0_bool: true, + level2_level3_arr_1_query: '${query5}', + level2_level3_arr_1_refId: 'E', + level2_level3_arr_1_num: 5, + level2_level3_arr_1_bool: true, + level2_level3_arr_1_arr_0_query: '${query6}', + level2_level3_arr_1_arr_0_refId: 'F', + level2_level3_arr_1_arr_0_num: 6, + level2_level3_arr_1_arr_0_bool: true, + arr_0_query: '${query7}', + arr_0_refId: 'G', + arr_0_num: 7, + arr_0_bool: true, + arr_1_query: '${query8}', + arr_1_refId: 'H', + arr_1_num: 8, + arr_1_bool: true, + arr_1_arr_0_query: '${query9}', + arr_1_arr_0_refId: 'I', + arr_1_arr_0_num: 9, + arr_1_arr_0_bool: true, + arr_1_arr_0_null: null, + }); + }); + + it('returns correct result when called with null', () => { + const query = null; + + expect(flattenQuery(query)).toEqual({ query: null }); + }); }); function mockDatasourceMetrics(variable: QueryVariableModel, optionsMetrics: any[]) { diff --git a/public/app/features/variables/query/actions.ts b/public/app/features/variables/query/actions.ts index f2777b32ada..f37b112b42d 100644 --- a/public/app/features/variables/query/actions.ts +++ b/public/app/features/variables/query/actions.ts @@ -179,14 +179,14 @@ export function hasSelfReferencingQuery(name: string, query: any): boolean { * Function that takes any object and flattens all props into one level deep object * */ export function flattenQuery(query: any): any { - if (typeof query !== 'object') { + if (typeof query !== 'object' || query === null) { return { query }; } const keys = Object.keys(query); const flattened = keys.reduce((all, key) => { const value = query[key]; - if (typeof value !== 'object') { + if (typeof value !== 'object' || value === null) { all[key] = value; return all; }