Commit 6994f19d by Hugo Häggmark Committed by GitHub

Variables: Clears drop down state when leaving dashboard (#30810)

parent eb83135b
...@@ -4,6 +4,7 @@ import { ...@@ -4,6 +4,7 @@ import {
changeVariableEditorExtended, changeVariableEditorExtended,
changeVariableNameFailed, changeVariableNameFailed,
changeVariableNameSucceeded, changeVariableNameSucceeded,
cleanEditorState,
clearIdInEditor, clearIdInEditor,
initialVariableEditorState, initialVariableEditorState,
removeVariableEditorError, removeVariableEditorError,
...@@ -17,7 +18,7 @@ import { toVariablePayload } from '../state/types'; ...@@ -17,7 +18,7 @@ import { toVariablePayload } from '../state/types';
describe('variableEditorReducer', () => { describe('variableEditorReducer', () => {
describe('when setIdInEditor is dispatched', () => { describe('when setIdInEditor is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { id: '0' }; const payload = { id: '0' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState })
...@@ -30,7 +31,7 @@ describe('variableEditorReducer', () => { ...@@ -30,7 +31,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when clearIdInEditor is dispatched', () => { describe('when clearIdInEditor is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState, id: '0' }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState, id: '0' })
.whenActionIsDispatched(clearIdInEditor()) .whenActionIsDispatched(clearIdInEditor())
...@@ -41,7 +42,7 @@ describe('variableEditorReducer', () => { ...@@ -41,7 +42,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when variableEditorMounted is dispatched', () => { describe('when variableEditorMounted is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { name: 'A name' }; const payload = { name: 'A name' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState })
...@@ -54,7 +55,7 @@ describe('variableEditorReducer', () => { ...@@ -54,7 +55,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when variableEditorUnMounted is dispatched', () => { describe('when variableEditorUnMounted is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const initialState = { const initialState = {
...initialVariableEditorState, ...initialVariableEditorState,
id: '0', id: '0',
...@@ -72,7 +73,7 @@ describe('variableEditorReducer', () => { ...@@ -72,7 +73,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when changeVariableNameSucceeded is dispatched there are other errors', () => { describe('when changeVariableNameSucceeded is dispatched there are other errors', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const initialState = { const initialState = {
...initialVariableEditorState, ...initialVariableEditorState,
name: 'A duplicate name', name: 'A duplicate name',
...@@ -93,7 +94,7 @@ describe('variableEditorReducer', () => { ...@@ -93,7 +94,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when changeVariableNameSucceeded is dispatched there are no other errors', () => { describe('when changeVariableNameSucceeded is dispatched there are no other errors', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const initialState = { const initialState = {
...initialVariableEditorState, ...initialVariableEditorState,
name: 'A duplicate name', name: 'A duplicate name',
...@@ -114,7 +115,7 @@ describe('variableEditorReducer', () => { ...@@ -114,7 +115,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when changeVariableNameFailed is dispatched', () => { describe('when changeVariableNameFailed is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { newName: 'Duplicate name', errorText: 'Name is an duplicate' }; const payload = { newName: 'Duplicate name', errorText: 'Name is an duplicate' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState })
...@@ -129,7 +130,7 @@ describe('variableEditorReducer', () => { ...@@ -129,7 +130,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when addVariableEditorError is dispatched', () => { describe('when addVariableEditorError is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { errorProp: 'someProp', errorText: 'someProp failed' }; const payload = { errorProp: 'someProp', errorText: 'someProp failed' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState })
...@@ -143,7 +144,7 @@ describe('variableEditorReducer', () => { ...@@ -143,7 +144,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when removeVariableEditorError is dispatched and there are other errors', () => { describe('when removeVariableEditorError is dispatched and there are other errors', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { errorProp: 'someProp' }; const payload = { errorProp: 'someProp' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { .givenReducer(variableEditorReducer, {
...@@ -161,7 +162,7 @@ describe('variableEditorReducer', () => { ...@@ -161,7 +162,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when removeVariableEditorError is dispatched and there are no other errors', () => { describe('when removeVariableEditorError is dispatched and there are no other errors', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { errorProp: 'someProp' }; const payload = { errorProp: 'someProp' };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { .givenReducer(variableEditorReducer, {
...@@ -179,7 +180,7 @@ describe('variableEditorReducer', () => { ...@@ -179,7 +180,7 @@ describe('variableEditorReducer', () => {
}); });
describe('when changeVariableEditorExtended is dispatched', () => { describe('when changeVariableEditorExtended is dispatched', () => {
it('then state should be correct ', () => { it('then state should be correct', () => {
const payload = { propName: 'someProp', propValue: [{}] }; const payload = { propName: 'someProp', propValue: [{}] };
reducerTester<VariableEditorState>() reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, { ...initialVariableEditorState }) .givenReducer(variableEditorReducer, { ...initialVariableEditorState })
...@@ -192,4 +193,18 @@ describe('variableEditorReducer', () => { ...@@ -192,4 +193,18 @@ describe('variableEditorReducer', () => {
}); });
}); });
}); });
describe('when cleanEditorState is dispatched', () => {
it('then state should be correct', () => {
reducerTester<VariableEditorState>()
.givenReducer(variableEditorReducer, {
...initialVariableEditorState,
isValid: false,
errors: { name: 'Name is an duplicate' },
name: 'Duplicate name',
})
.whenActionIsDispatched(cleanEditorState())
.thenStateShouldEqual({ ...initialVariableEditorState });
});
});
}); });
...@@ -70,6 +70,7 @@ const variableEditorReducerSlice = createSlice({ ...@@ -70,6 +70,7 @@ const variableEditorReducerSlice = createSlice({
[action.payload.propName]: action.payload.propValue, [action.payload.propName]: action.payload.propValue,
}; };
}, },
cleanEditorState: () => initialVariableEditorState,
}, },
}); });
...@@ -85,4 +86,5 @@ export const { ...@@ -85,4 +86,5 @@ export const {
changeVariableEditorExtended, changeVariableEditorExtended,
addVariableEditorError, addVariableEditorError,
removeVariableEditorError, removeVariableEditorError,
cleanEditorState,
} = variableEditorReducerSlice.actions; } = variableEditorReducerSlice.actions;
import { cloneDeep } from 'lodash'; import { cloneDeep } from 'lodash';
import { import {
cleanPickerState,
hideOptions, hideOptions,
initialState as optionsPickerInitialState, initialState as optionsPickerInitialState,
moveOptionsHighlight, moveOptionsHighlight,
...@@ -941,4 +942,22 @@ describe('optionsPickerReducer', () => { ...@@ -941,4 +942,22 @@ describe('optionsPickerReducer', () => {
}); });
}); });
}); });
describe('when cleanPickerState is dispatched', () => {
it('then state should be correct', () => {
const { initialState } = getVariableTestContext({
highlightIndex: 19,
multi: true,
id: 'some id',
options: [{ text: 'A', value: 'A', selected: true }],
queryValue: 'a query value',
selectedValues: [{ text: 'A', value: 'A', selected: true }],
});
reducerTester<OptionsPickerState>()
.givenReducer(optionsPickerReducer, cloneDeep(initialState))
.whenActionIsDispatched(cleanPickerState())
.thenStateShouldEqual({ ...optionsPickerInitialState });
});
});
}); });
...@@ -252,6 +252,7 @@ const optionsPickerSlice = createSlice({ ...@@ -252,6 +252,7 @@ const optionsPickerSlice = createSlice({
return applyStateChanges(state, updateDefaultSelection, updateOptions); return applyStateChanges(state, updateDefaultSelection, updateOptions);
}, },
cleanPickerState: () => initialState,
}, },
}); });
...@@ -265,6 +266,7 @@ export const { ...@@ -265,6 +266,7 @@ export const {
updateSearchQuery, updateSearchQuery,
updateOptionsAndFilter, updateOptionsAndFilter,
updateOptionsFromSearch, updateOptionsFromSearch,
cleanPickerState,
} = optionsPickerSlice.actions; } = optionsPickerSlice.actions;
export const optionsPickerReducer = optionsPickerSlice.reducer; export const optionsPickerReducer = optionsPickerSlice.reducer;
...@@ -45,6 +45,7 @@ import { changeVariableName } from '../editor/actions'; ...@@ -45,6 +45,7 @@ import { changeVariableName } from '../editor/actions';
import { import {
changeVariableNameFailed, changeVariableNameFailed,
changeVariableNameSucceeded, changeVariableNameSucceeded,
cleanEditorState,
initialVariableEditorState, initialVariableEditorState,
setIdInEditor, setIdInEditor,
} from '../editor/reducer'; } from '../editor/reducer';
...@@ -55,7 +56,7 @@ import { ...@@ -55,7 +56,7 @@ import {
variablesCompleteTransaction, variablesCompleteTransaction,
variablesInitTransaction, variablesInitTransaction,
} from './transactionReducer'; } from './transactionReducer';
import { initialState } from '../pickers/OptionsPicker/reducer'; import { cleanPickerState, initialState } from '../pickers/OptionsPicker/reducer';
import { cleanVariables } from './variablesReducer'; import { cleanVariables } from './variablesReducer';
import { expect } from '../../../../test/lib/common'; import { expect } from '../../../../test/lib/common';
import { ConstantVariableModel, VariableRefresh } from '../types'; import { ConstantVariableModel, VariableRefresh } from '../types';
...@@ -612,21 +613,23 @@ describe('shared actions', () => { ...@@ -612,21 +613,23 @@ describe('shared actions', () => {
tester.thenDispatchedActionsPredicateShouldEqual((dispatchedActions) => { tester.thenDispatchedActionsPredicateShouldEqual((dispatchedActions) => {
expect(dispatchedActions[0]).toEqual(cleanVariables()); expect(dispatchedActions[0]).toEqual(cleanVariables());
expect(dispatchedActions[1]).toEqual(variablesClearTransaction()); expect(dispatchedActions[1]).toEqual(cleanEditorState());
expect(dispatchedActions[2]).toEqual(variablesInitTransaction({ uid })); expect(dispatchedActions[2]).toEqual(cleanPickerState());
expect(dispatchedActions[3].type).toEqual(addVariable.type); expect(dispatchedActions[3]).toEqual(variablesClearTransaction());
expect(dispatchedActions[3].payload.id).toEqual('__dashboard'); expect(dispatchedActions[4]).toEqual(variablesInitTransaction({ uid }));
expect(dispatchedActions[4].type).toEqual(addVariable.type);
expect(dispatchedActions[4].payload.id).toEqual('__org');
expect(dispatchedActions[5].type).toEqual(addVariable.type); expect(dispatchedActions[5].type).toEqual(addVariable.type);
expect(dispatchedActions[5].payload.id).toEqual('__user'); expect(dispatchedActions[5].payload.id).toEqual('__dashboard');
expect(dispatchedActions[6]).toEqual( expect(dispatchedActions[6].type).toEqual(addVariable.type);
expect(dispatchedActions[6].payload.id).toEqual('__org');
expect(dispatchedActions[7].type).toEqual(addVariable.type);
expect(dispatchedActions[7].payload.id).toEqual('__user');
expect(dispatchedActions[8]).toEqual(
addVariable(toVariablePayload(constant, { global: false, index: 0, model: constant })) addVariable(toVariablePayload(constant, { global: false, index: 0, model: constant }))
); );
expect(dispatchedActions[7]).toEqual(variableStateNotStarted(toVariablePayload(constant))); expect(dispatchedActions[9]).toEqual(variableStateNotStarted(toVariablePayload(constant)));
expect(dispatchedActions[8]).toEqual(variableStateCompleted(toVariablePayload(constant))); expect(dispatchedActions[10]).toEqual(variableStateCompleted(toVariablePayload(constant)));
expect(dispatchedActions[9]).toEqual(variablesCompleteTransaction({ uid })); expect(dispatchedActions[11]).toEqual(variablesCompleteTransaction({ uid }));
return dispatchedActions.length === 10; return dispatchedActions.length === 12;
}); });
}); });
}); });
...@@ -638,7 +641,12 @@ describe('shared actions', () => { ...@@ -638,7 +641,12 @@ describe('shared actions', () => {
reduxTester<{ templating: TemplatingState }>() reduxTester<{ templating: TemplatingState }>()
.givenRootReducer(getTemplatingRootReducer()) .givenRootReducer(getTemplatingRootReducer())
.whenActionIsDispatched(cleanUpVariables()) .whenActionIsDispatched(cleanUpVariables())
.thenDispatchedActionsShouldEqual(cleanVariables(), variablesClearTransaction()); .thenDispatchedActionsShouldEqual(
cleanVariables(),
cleanEditorState(),
cleanPickerState(),
variablesClearTransaction()
);
}); });
}); });
}); });
...@@ -654,7 +662,12 @@ describe('shared actions', () => { ...@@ -654,7 +662,12 @@ describe('shared actions', () => {
reduxTester<{ templating: TemplatingState }>() reduxTester<{ templating: TemplatingState }>()
.givenRootReducer(getTemplatingRootReducer()) .givenRootReducer(getTemplatingRootReducer())
.whenActionIsDispatched(cancelVariables({ getBackendSrv: () => backendSrvMock })) .whenActionIsDispatched(cancelVariables({ getBackendSrv: () => backendSrvMock }))
.thenDispatchedActionsShouldEqual(cleanVariables(), variablesClearTransaction()); .thenDispatchedActionsShouldEqual(
cleanVariables(),
cleanEditorState(),
cleanPickerState(),
variablesClearTransaction()
);
expect(cancelAllInFlightRequestsMock).toHaveBeenCalledTimes(1); expect(cancelAllInFlightRequestsMock).toHaveBeenCalledTimes(1);
}); });
......
...@@ -55,6 +55,8 @@ import isEqual from 'lodash/isEqual'; ...@@ -55,6 +55,8 @@ import isEqual from 'lodash/isEqual';
import { getCurrentText, getVariableRefresh } from '../utils'; import { getCurrentText, getVariableRefresh } from '../utils';
import { store } from 'app/store/store'; import { store } from 'app/store/store';
import { getDatasourceSrv } from '../../plugins/datasource_srv'; import { getDatasourceSrv } from '../../plugins/datasource_srv';
import { cleanEditorState } from '../editor/reducer';
import { cleanPickerState } from '../pickers/OptionsPicker/reducer';
// process flow queryVariable // process flow queryVariable
// thunk => processVariables // thunk => processVariables
...@@ -621,6 +623,8 @@ export const initVariablesTransaction = (dashboardUid: string, dashboard: Dashbo ...@@ -621,6 +623,8 @@ export const initVariablesTransaction = (dashboardUid: string, dashboard: Dashbo
export const cleanUpVariables = (): ThunkResult<void> => (dispatch) => { export const cleanUpVariables = (): ThunkResult<void> => (dispatch) => {
dispatch(cleanVariables()); dispatch(cleanVariables());
dispatch(cleanEditorState());
dispatch(cleanPickerState());
dispatch(variablesClearTransaction()); dispatch(variablesClearTransaction());
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment