Commit 033dff27 authored by Ezekiel Kigbo's avatar Ezekiel Kigbo Committed by Kushal Pandya

Remove cycleAnalyticsScatterplotMedianEnabled feature flag

Removes the request for the duration
chart median value
parent afa79d13
...@@ -350,15 +350,6 @@ administrator can open a Rails console and disable it with the following command ...@@ -350,15 +350,6 @@ administrator can open a Rails console and disable it with the following command
Feature.disable(:cycle_analytics_scatterplot_enabled) Feature.disable(:cycle_analytics_scatterplot_enabled)
``` ```
### Disabling chart median line
This chart's median line is enabled by default. If you have a self-managed instance, an
administrator can open a Rails console and disable it with the following command:
```ruby
Feature.disable(:cycle_analytics_scatterplot_median_enabled)
```
## Type of work - Tasks by type chart ## Type of work - Tasks by type chart
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/32421) in GitLab 12.10. > [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/32421) in GitLab 12.10.
......
...@@ -20,7 +20,7 @@ export default { ...@@ -20,7 +20,7 @@ export default {
}, },
computed: { computed: {
...mapState('durationChart', ['isLoading']), ...mapState('durationChart', ['isLoading']),
...mapGetters('durationChart', ['durationChartPlottableData', 'durationChartMedianData']), ...mapGetters('durationChart', ['durationChartPlottableData']),
hasData() { hasData() {
return Boolean(this.durationChartPlottableData.length); return Boolean(this.durationChartPlottableData.length);
}, },
...@@ -53,7 +53,6 @@ export default { ...@@ -53,7 +53,6 @@ export default {
:y-axis-title="s__('CycleAnalytics|Total days to completion')" :y-axis-title="s__('CycleAnalytics|Total days to completion')"
:tooltip-date-format="$options.durationChartTooltipDateFormat" :tooltip-date-format="$options.durationChartTooltipDateFormat"
:scatter-data="durationChartPlottableData" :scatter-data="durationChartPlottableData"
:median-line-data="durationChartMedianData"
/> />
<div v-else ref="duration-chart-no-data" class="bs-callout bs-callout-info"> <div v-else ref="duration-chart-no-data" class="bs-callout bs-callout-info">
{{ __('There is no data available. Please change your selection.') }} {{ __('There is no data available. Please change your selection.') }}
......
...@@ -14,7 +14,6 @@ export default () => { ...@@ -14,7 +14,6 @@ export default () => {
const store = createStore(); const store = createStore();
const { const {
cycleAnalyticsScatterplotEnabled: hasDurationChart = false, cycleAnalyticsScatterplotEnabled: hasDurationChart = false,
cycleAnalyticsScatterplotMedianEnabled: hasDurationChartMedian = false,
valueStreamAnalyticsPathNavigation: hasPathNavigation = false, valueStreamAnalyticsPathNavigation: hasPathNavigation = false,
valueStreamAnalyticsCreateMultipleValueStreams: hasCreateMultipleValueStreams = false, valueStreamAnalyticsCreateMultipleValueStreams: hasCreateMultipleValueStreams = false,
analyticsSimilaritySearch: hasAnalyticsSimilaritySearch = false, analyticsSimilaritySearch: hasAnalyticsSimilaritySearch = false,
...@@ -24,7 +23,6 @@ export default () => { ...@@ -24,7 +23,6 @@ export default () => {
...initialData, ...initialData,
featureFlags: { featureFlags: {
hasDurationChart, hasDurationChart,
hasDurationChartMedian,
hasPathNavigation, hasPathNavigation,
hasCreateMultipleValueStreams, hasCreateMultipleValueStreams,
hasAnalyticsSimilaritySearch, hasAnalyticsSimilaritySearch,
......
import dateFormat from 'dateformat';
import Api from 'ee/api'; import Api from 'ee/api';
import { getDayDifference, getDateInPast } from '~/lib/utils/datetime_utility';
import { deprecatedCreateFlash as createFlash } from '~/flash'; import { deprecatedCreateFlash as createFlash } from '~/flash';
import { __ } from '~/locale'; import { __ } from '~/locale';
import * as types from './mutation_types'; import * as types from './mutation_types';
import { dateFormats } from '../../../../shared/constants';
export const requestDurationData = ({ commit }) => commit(types.REQUEST_DURATION_DATA); export const requestDurationData = ({ commit }) => commit(types.REQUEST_DURATION_DATA);
export const receiveDurationDataSuccess = ({ commit, rootState, dispatch }, data) => {
commit(types.RECEIVE_DURATION_DATA_SUCCESS, data);
const { featureFlags: { hasDurationChartMedian = false } = {} } = rootState;
if (hasDurationChartMedian) dispatch('fetchDurationMedianData');
};
export const receiveDurationDataError = ({ commit }) => { export const receiveDurationDataError = ({ commit }) => {
commit(types.RECEIVE_DURATION_DATA_ERROR); commit(types.RECEIVE_DURATION_DATA_ERROR);
createFlash(__('There was an error while fetching value stream analytics duration data.')); createFlash(__('There was an error while fetching value stream analytics duration data.'));
}; };
export const fetchDurationData = ({ dispatch, rootGetters }) => { export const fetchDurationData = ({ dispatch, commit, rootGetters }) => {
dispatch('requestDurationData'); dispatch('requestDurationData');
const { const {
cycleAnalyticsRequestParams, cycleAnalyticsRequestParams,
...@@ -44,50 +34,10 @@ export const fetchDurationData = ({ dispatch, rootGetters }) => { ...@@ -44,50 +34,10 @@ export const fetchDurationData = ({ dispatch, rootGetters }) => {
})); }));
}), }),
) )
.then(data => dispatch('receiveDurationDataSuccess', data)) .then(data => commit(types.RECEIVE_DURATION_DATA_SUCCESS, data))
.catch(() => dispatch('receiveDurationDataError')); .catch(() => dispatch('receiveDurationDataError'));
}; };
export const receiveDurationMedianDataSuccess = ({ commit }, data) =>
commit(types.RECEIVE_DURATION_MEDIAN_DATA_SUCCESS, data);
export const receiveDurationMedianDataError = ({ commit }) => {
commit(types.RECEIVE_DURATION_MEDIAN_DATA_ERROR);
createFlash(__('There was an error while fetching value stream analytics duration median data.'));
};
export const fetchDurationMedianData = ({ dispatch, rootState, rootGetters }) => {
const { startDate, endDate } = rootState;
const {
cycleAnalyticsRequestParams,
activeStages,
currentGroupPath,
currentValueStreamId,
} = rootGetters;
const offsetValue = getDayDifference(new Date(startDate), new Date(endDate));
const offsetCreatedAfter = getDateInPast(new Date(startDate), offsetValue);
const offsetCreatedBefore = getDateInPast(new Date(endDate), offsetValue);
return Promise.all(
activeStages.map(stage => {
const { slug } = stage;
return Api.cycleAnalyticsDurationChart(currentGroupPath, currentValueStreamId, slug, {
...cycleAnalyticsRequestParams,
created_after: dateFormat(offsetCreatedAfter, dateFormats.isoDate),
created_before: dateFormat(offsetCreatedBefore, dateFormats.isoDate),
}).then(({ data }) => ({
slug,
selected: true,
data,
}));
}),
)
.then(data => dispatch('receiveDurationMedianDataSuccess', data))
.catch(() => dispatch('receiveDurationMedianDataError'));
};
export const updateSelectedDurationChartStages = ({ state, commit }, stages) => { export const updateSelectedDurationChartStages = ({ state, commit }, stages) => {
const setSelectedPropertyOnStages = data => const setSelectedPropertyOnStages = data =>
data.map(stage => { data.map(stage => {
...@@ -102,12 +52,10 @@ export const updateSelectedDurationChartStages = ({ state, commit }, stages) => ...@@ -102,12 +52,10 @@ export const updateSelectedDurationChartStages = ({ state, commit }, stages) =>
}; };
}); });
const { durationData, durationMedianData } = state; const { durationData } = state;
const updatedDurationStageData = setSelectedPropertyOnStages(durationData); const updatedDurationStageData = setSelectedPropertyOnStages(durationData);
const updatedDurationStageMedianData = setSelectedPropertyOnStages(durationMedianData);
commit(types.UPDATE_SELECTED_DURATION_CHART_STAGES, { commit(types.UPDATE_SELECTED_DURATION_CHART_STAGES, {
updatedDurationStageData, updatedDurationStageData,
updatedDurationStageMedianData,
}); });
}; };
import { getDurationChartData, getDurationChartMedianData } from '../../../utils'; import { getDurationChartData } from '../../../utils';
export const durationChartPlottableData = (state, _, rootState) => { export const durationChartPlottableData = (state, _, rootState) => {
const { startDate, endDate } = rootState; const { startDate, endDate } = rootState;
...@@ -8,16 +8,3 @@ export const durationChartPlottableData = (state, _, rootState) => { ...@@ -8,16 +8,3 @@ export const durationChartPlottableData = (state, _, rootState) => {
return plottableData.length ? plottableData : []; return plottableData.length ? plottableData : [];
}; };
export const durationChartMedianData = (state, _, rootState) => {
const { startDate, endDate } = rootState;
const { durationMedianData } = state;
const selectedStagesDurationMedianData = durationMedianData.filter(stage => stage.selected);
const plottableData = getDurationChartMedianData(
selectedStagesDurationMedianData,
startDate,
endDate,
);
return plottableData.length ? plottableData : [];
};
...@@ -3,6 +3,3 @@ export const UPDATE_SELECTED_DURATION_CHART_STAGES = 'UPDATE_SELECTED_DURATION_C ...@@ -3,6 +3,3 @@ export const UPDATE_SELECTED_DURATION_CHART_STAGES = 'UPDATE_SELECTED_DURATION_C
export const REQUEST_DURATION_DATA = 'REQUEST_DURATION_DATA'; export const REQUEST_DURATION_DATA = 'REQUEST_DURATION_DATA';
export const RECEIVE_DURATION_DATA_SUCCESS = 'RECEIVE_DURATION_DATA_SUCCESS'; export const RECEIVE_DURATION_DATA_SUCCESS = 'RECEIVE_DURATION_DATA_SUCCESS';
export const RECEIVE_DURATION_DATA_ERROR = 'RECEIVE_DURATION_DATA_ERROR'; export const RECEIVE_DURATION_DATA_ERROR = 'RECEIVE_DURATION_DATA_ERROR';
export const RECEIVE_DURATION_MEDIAN_DATA_SUCCESS = 'RECEIVE_DURATION_MEDIAN_DATA_SUCCESS';
export const RECEIVE_DURATION_MEDIAN_DATA_ERROR = 'RECEIVE_DURATION_MEDIAN_DATA_ERROR';
import * as types from './mutation_types'; import * as types from './mutation_types';
export default { export default {
[types.UPDATE_SELECTED_DURATION_CHART_STAGES]( [types.UPDATE_SELECTED_DURATION_CHART_STAGES](state, { updatedDurationStageData }) {
state,
{ updatedDurationStageData, updatedDurationStageMedianData },
) {
state.durationData = updatedDurationStageData; state.durationData = updatedDurationStageData;
state.durationMedianData = updatedDurationStageMedianData;
}, },
[types.REQUEST_DURATION_DATA](state) { [types.REQUEST_DURATION_DATA](state) {
state.isLoading = true; state.isLoading = true;
...@@ -19,10 +15,4 @@ export default { ...@@ -19,10 +15,4 @@ export default {
state.durationData = []; state.durationData = [];
state.isLoading = false; state.isLoading = false;
}, },
[types.RECEIVE_DURATION_MEDIAN_DATA_SUCCESS](state, data) {
state.durationMedianData = data;
},
[types.RECEIVE_DURATION_MEDIAN_DATA_ERROR](state) {
state.durationMedianData = [];
},
}; };
...@@ -2,5 +2,4 @@ export default () => ({ ...@@ -2,5 +2,4 @@ export default () => ({
isLoading: false, isLoading: false,
durationData: [], durationData: [],
durationMedianData: [],
}); });
...@@ -10,9 +10,6 @@ import { ...@@ -10,9 +10,6 @@ import {
dayAfter, dayAfter,
secondsToDays, secondsToDays,
getDatesInRange, getDatesInRange,
getDayDifference,
getDateInPast,
getDateInFuture,
parseSeconds, parseSeconds,
} from '~/lib/utils/datetime_utility'; } from '~/lib/utils/datetime_utility';
import { dateFormats } from '../shared/constants'; import { dateFormats } from '../shared/constants';
...@@ -215,42 +212,6 @@ export const getDurationChartData = (data, startDate, endDate) => { ...@@ -215,42 +212,6 @@ export const getDurationChartData = (data, startDate, endDate) => {
return eventData; return eventData;
}; };
/**
* Takes the offset duration data for selected stages and calls getDurationChartData to compute the totals.
* The data is then transformed into a format expected by the scatterplot;
*
* [
* ['2019-09-02', 7],
* ...
* ]
*
* The transformation works by calling getDateInPast on the provided startDate and endDate in order to match
* the startDate and endDate fetched when making the API call to fetch the data.
*
* In order to map the offset data to plottable points within the chart's range, getDateInFuture is called
* on the data series with the same offest used for getDateInPast. This creates plottable data that matches up
* with the data being displayed on the chart.
*
* @param {Array} data - The computed, plottable duration chart data
* @param {Date} startDate - The globally selected cycle analytics start date
* @param {Date} endDate - The globally selected cycle analytics end date
* @returns {Array} An array with each item being another arry of two items (date, computed total)
*/
export const getDurationChartMedianData = (data, startDate, endDate) => {
const offsetValue = getDayDifference(startDate, endDate);
const offsetEndDate = getDateInPast(endDate, offsetValue);
const offsetStartDate = getDateInPast(startDate, offsetValue);
const offsetDurationData = getDurationChartData(data, offsetStartDate, offsetEndDate);
const result = offsetDurationData.map(event => [
dateFormat(getDateInFuture(new Date(event[0]), offsetValue), dateFormats.isoDate),
event[1],
]);
return result;
};
export const orderByDate = (a, b, dateFmt = datetime => new Date(datetime).getTime()) => export const orderByDate = (a, b, dateFmt = datetime => new Date(datetime).getTime()) =>
dateFmt(a) - dateFmt(b); dateFmt(a) - dateFmt(b);
......
...@@ -13,7 +13,6 @@ class Analytics::CycleAnalyticsController < Analytics::ApplicationController ...@@ -13,7 +13,6 @@ class Analytics::CycleAnalyticsController < Analytics::ApplicationController
before_action do before_action do
push_frontend_feature_flag(:cycle_analytics_scatterplot_enabled, default_enabled: true) push_frontend_feature_flag(:cycle_analytics_scatterplot_enabled, default_enabled: true)
push_frontend_feature_flag(:cycle_analytics_scatterplot_median_enabled, default_enabled: true)
push_frontend_feature_flag(:value_stream_analytics_path_navigation, @group) push_frontend_feature_flag(:value_stream_analytics_path_navigation, @group)
push_frontend_feature_flag(:value_stream_analytics_create_multiple_value_streams, default_enabled: true) push_frontend_feature_flag(:value_stream_analytics_create_multiple_value_streams, default_enabled: true)
push_frontend_feature_flag(:analytics_similarity_search, @group, default_enabled: true) push_frontend_feature_flag(:analytics_similarity_search, @group, default_enabled: true)
......
---
title: Remove VSA duration median line
merge_request: 39665
author:
type: removed
...@@ -19,7 +19,6 @@ RSpec.describe 'Group value stream analytics' do ...@@ -19,7 +19,6 @@ RSpec.describe 'Group value stream analytics' do
expect(page).to have_pushed_frontend_feature_flags( expect(page).to have_pushed_frontend_feature_flags(
cycleAnalyticsScatterplotEnabled: true, cycleAnalyticsScatterplotEnabled: true,
cycleAnalyticsScatterplotMedianEnabled: true,
valueStreamAnalyticsPathNavigation: true, valueStreamAnalyticsPathNavigation: true,
analyticsSimilaritySearch: true analyticsSimilaritySearch: true
) )
......
...@@ -6,6 +6,6 @@ exports[`DurationChart renders the duration chart 1`] = ` ...@@ -6,6 +6,6 @@ exports[`DurationChart renders the duration chart 1`] = `
<h4 class=\\"mt-0\\">Days to completion</h4> <h4 class=\\"mt-0\\">Days to completion</h4>
<stagedropdownfilter-stub stages=\\"[object Object],[object Object],[object Object]\\" label=\\"stage dropdown\\" class=\\"ml-auto\\"></stagedropdownfilter-stub> <stagedropdownfilter-stub stages=\\"[object Object],[object Object],[object Object]\\" label=\\"stage dropdown\\" class=\\"ml-auto\\"></stagedropdownfilter-stub>
</div> </div>
<scatterplot-stub xaxistitle=\\"Date\\" yaxistitle=\\"Total days to completion\\" scatterdata=\\"2019-01-01,29,2019-01-01,2019-01-02,100,2019-01-02\\" medianlinedata=\\"2018-12-31,29,2019-01-01,100\\" tooltipdateformat=\\"mmm d, yyyy\\"></scatterplot-stub> <scatterplot-stub xaxistitle=\\"Date\\" yaxistitle=\\"Total days to completion\\" scatterdata=\\"2019-01-01,29,2019-01-01,2019-01-02,100,2019-01-02\\" medianlinedata=\\"\\" tooltipdateformat=\\"mmm d, yyyy\\"></scatterplot-stub>
</div>" </div>"
`; `;
...@@ -50,7 +50,6 @@ const defaultStubs = { ...@@ -50,7 +50,6 @@ const defaultStubs = {
const defaultFeatureFlags = { const defaultFeatureFlags = {
hasDurationChart: true, hasDurationChart: true,
hasDurationChartMedian: true,
hasPathNavigation: false, hasPathNavigation: false,
hasCreateMultipleValueStreams: false, hasCreateMultipleValueStreams: false,
}; };
......
...@@ -5,11 +5,7 @@ import durationChartStore from 'ee/analytics/cycle_analytics/store/modules/durat ...@@ -5,11 +5,7 @@ import durationChartStore from 'ee/analytics/cycle_analytics/store/modules/durat
import Scatterplot from 'ee/analytics/shared/components/scatterplot.vue'; import Scatterplot from 'ee/analytics/shared/components/scatterplot.vue';
import DurationChart from 'ee/analytics/cycle_analytics/components/duration_chart.vue'; import DurationChart from 'ee/analytics/cycle_analytics/components/duration_chart.vue';
import StageDropdownFilter from 'ee/analytics/cycle_analytics/components/stage_dropdown_filter.vue'; import StageDropdownFilter from 'ee/analytics/cycle_analytics/components/stage_dropdown_filter.vue';
import { import { allowedStages as stages, durationChartPlottableData as durationData } from '../mock_data';
allowedStages as stages,
durationChartPlottableData as durationData,
durationChartPlottableMedianData as durationMedianData,
} from '../mock_data';
const localVue = createLocalVue(); const localVue = createLocalVue();
localVue.use(Vuex); localVue.use(Vuex);
...@@ -26,7 +22,6 @@ const fakeStore = ({ initialGetters, initialState }) => ...@@ -26,7 +22,6 @@ const fakeStore = ({ initialGetters, initialState }) =>
...durationChartStore, ...durationChartStore,
getters: { getters: {
durationChartPlottableData: () => durationData, durationChartPlottableData: () => durationData,
durationChartMedianData: () => durationMedianData,
...initialGetters, ...initialGetters,
}, },
state: { state: {
...@@ -130,7 +125,6 @@ describe('DurationChart', () => { ...@@ -130,7 +125,6 @@ describe('DurationChart', () => {
wrapper = createComponent({ wrapper = createComponent({
initialGetters: { initialGetters: {
durationChartPlottableData: () => [], durationChartPlottableData: () => [],
durationChartMedianData: () => [],
}, },
}); });
}); });
......
...@@ -252,21 +252,6 @@ export const rawDurationMedianData = [ ...@@ -252,21 +252,6 @@ export const rawDurationMedianData = [
}, },
]; ];
export const transformedDurationMedianData = [
{
slug: 1,
selected: true,
data: rawDurationMedianData,
},
{
slug: 2,
selected: true,
data: rawDurationMedianData,
},
];
export const durationChartPlottableMedianData = [['2018-12-31', 29], ['2019-01-01', 100]];
export const selectedProjects = [ export const selectedProjects = [
{ {
id: 1, id: 1,
......
...@@ -58,7 +58,6 @@ describe('Cycle analytics actions', () => { ...@@ -58,7 +58,6 @@ describe('Cycle analytics actions', () => {
stages: [], stages: [],
featureFlags: { featureFlags: {
hasDurationChart: true, hasDurationChart: true,
hasDurationChartMedian: true,
}, },
activeStages, activeStages,
selectedValueStream, selectedValueStream,
......
...@@ -11,9 +11,7 @@ import { ...@@ -11,9 +11,7 @@ import {
startDate, startDate,
endDate, endDate,
rawDurationData, rawDurationData,
rawDurationMedianData,
transformedDurationData, transformedDurationData,
transformedDurationMedianData,
endpoints, endpoints,
valueStreams, valueStreams,
} from '../../../mock_data'; } from '../../../mock_data';
...@@ -33,7 +31,6 @@ const rootState = { ...@@ -33,7 +31,6 @@ const rootState = {
selectedValueStream, selectedValueStream,
featureFlags: { featureFlags: {
hasDurationChart: true, hasDurationChart: true,
hasDurationChartMedian: true,
}, },
}; };
...@@ -66,14 +63,13 @@ describe('DurationChart actions', () => { ...@@ -66,14 +63,13 @@ describe('DurationChart actions', () => {
actions.fetchDurationData, actions.fetchDurationData,
null, null,
state, state,
[],
[ [
{ type: 'requestDurationData' },
{ {
type: 'receiveDurationDataSuccess', type: types.RECEIVE_DURATION_DATA_SUCCESS,
payload: transformedDurationData, payload: transformedDurationData,
}, },
], ],
[{ type: 'requestDurationData' }],
); );
}); });
...@@ -120,53 +116,6 @@ describe('DurationChart actions', () => { ...@@ -120,53 +116,6 @@ describe('DurationChart actions', () => {
}); });
}); });
describe('receiveDurationDataSuccess', () => {
describe('with hasDurationChartMedian feature flag enabled', () => {
it('commits the transformed duration data and dispatches fetchDurationMedianData', () => {
testAction(
actions.receiveDurationDataSuccess,
transformedDurationData,
rootState,
[
{
type: types.RECEIVE_DURATION_DATA_SUCCESS,
payload: transformedDurationData,
},
],
[
{
type: 'fetchDurationMedianData',
},
],
);
});
});
describe('with hasDurationChartMedian feature flag disabled', () => {
const disabledState = {
...rootState,
featureFlags: {
hasDurationChartMedian: false,
},
};
it('commits the transformed duration data', () => {
testAction(
actions.receiveDurationDataSuccess,
transformedDurationData,
disabledState,
[
{
type: types.RECEIVE_DURATION_DATA_SUCCESS,
payload: transformedDurationData,
},
],
[],
);
});
});
});
describe('receiveDurationDataError', () => { describe('receiveDurationDataError', () => {
beforeEach(() => { beforeEach(() => {
setFixtures('<div class="flash-container"></div>'); setFixtures('<div class="flash-container"></div>');
...@@ -202,7 +151,6 @@ describe('DurationChart actions', () => { ...@@ -202,7 +151,6 @@ describe('DurationChart actions', () => {
const stateWithDurationData = { const stateWithDurationData = {
...state, ...state,
durationData: transformedDurationData, durationData: transformedDurationData,
durationMedianData: transformedDurationMedianData,
}; };
testAction( testAction(
...@@ -214,7 +162,6 @@ describe('DurationChart actions', () => { ...@@ -214,7 +162,6 @@ describe('DurationChart actions', () => {
type: types.UPDATE_SELECTED_DURATION_CHART_STAGES, type: types.UPDATE_SELECTED_DURATION_CHART_STAGES,
payload: { payload: {
updatedDurationStageData: transformedDurationData, updatedDurationStageData: transformedDurationData,
updatedDurationStageMedianData: transformedDurationMedianData,
}, },
}, },
], ],
...@@ -226,7 +173,6 @@ describe('DurationChart actions', () => { ...@@ -226,7 +173,6 @@ describe('DurationChart actions', () => {
const stateWithDurationData = { const stateWithDurationData = {
...state, ...state,
durationData: transformedDurationData, durationData: transformedDurationData,
durationMedianData: transformedDurationMedianData,
}; };
testAction( testAction(
...@@ -244,13 +190,6 @@ describe('DurationChart actions', () => { ...@@ -244,13 +190,6 @@ describe('DurationChart actions', () => {
selected: false, selected: false,
}, },
], ],
updatedDurationStageMedianData: [
transformedDurationMedianData[0],
{
...transformedDurationMedianData[1],
selected: false,
},
],
}, },
}, },
], ],
...@@ -262,7 +201,6 @@ describe('DurationChart actions', () => { ...@@ -262,7 +201,6 @@ describe('DurationChart actions', () => {
const stateWithDurationData = { const stateWithDurationData = {
...state, ...state,
durationData: transformedDurationData, durationData: transformedDurationData,
durationMedianData: transformedDurationMedianData,
}; };
testAction( testAction(
...@@ -283,16 +221,6 @@ describe('DurationChart actions', () => { ...@@ -283,16 +221,6 @@ describe('DurationChart actions', () => {
selected: false, selected: false,
}, },
], ],
updatedDurationStageMedianData: [
{
...transformedDurationMedianData[0],
selected: false,
},
{
...transformedDurationMedianData[1],
selected: false,
},
],
}, },
}, },
], ],
...@@ -300,95 +228,4 @@ describe('DurationChart actions', () => { ...@@ -300,95 +228,4 @@ describe('DurationChart actions', () => {
); );
}); });
}); });
describe('fetchDurationMedianData', () => {
beforeEach(() => {
mock.onGet(endpoints.durationData).reply(200, [...rawDurationMedianData]);
});
it('dispatches the receiveDurationMedianDataSuccess action on success', () => {
return testAction(
actions.fetchDurationMedianData,
null,
state,
[],
[
{
type: 'receiveDurationMedianDataSuccess',
payload: transformedDurationMedianData,
},
],
);
});
describe('receiveDurationMedianDataError', () => {
beforeEach(() => {
mock.onGet(endpoints.durationData).reply(404);
});
it('dispatches the receiveDurationMedianDataError action when there is an error', () => {
const dispatch = jest.fn();
return actions
.fetchDurationMedianData({
dispatch,
rootState,
rootGetters: { ...rootGetters, activeStages },
})
.then(() => {
const requestedUrls = mock.history.get.map(({ url }) => url);
expect(requestedUrls).not.toContain(
`/groups/foo/-/analytics/value_stream_analytics/stages/${hiddenStage.id}/duration_chart`,
);
expect(dispatch).toHaveBeenCalledWith('receiveDurationMedianDataError');
});
});
});
});
describe('receiveDurationMedianDataSuccess', () => {
it('commits the transformed duration median data', () => {
return testAction(
actions.receiveDurationMedianDataSuccess,
transformedDurationMedianData,
rootState,
[
{
type: types.RECEIVE_DURATION_MEDIAN_DATA_SUCCESS,
payload: transformedDurationMedianData,
},
],
[],
);
});
});
describe('receiveDurationMedianDataError', () => {
beforeEach(() => {
setFixtures('<div class="flash-container"></div>');
});
it("commits the 'RECEIVE_DURATION_MEDIAN_DATA_ERROR' mutation", () => {
return testAction(
actions.receiveDurationMedianDataError,
{},
rootState,
[
{
type: types.RECEIVE_DURATION_MEDIAN_DATA_ERROR,
},
],
[],
);
});
it('will flash an error', () => {
actions.receiveDurationMedianDataError({
commit: () => {},
});
shouldFlashAMessage(
'There was an error while fetching value stream analytics duration median data.',
);
});
});
}); });
...@@ -3,9 +3,7 @@ import { ...@@ -3,9 +3,7 @@ import {
startDate, startDate,
endDate, endDate,
transformedDurationData, transformedDurationData,
transformedDurationMedianData,
durationChartPlottableData, durationChartPlottableData,
durationChartPlottableMedianData,
} from '../../../mock_data'; } from '../../../mock_data';
const rootState = { const rootState = {
...@@ -35,28 +33,4 @@ describe('DurationChart getters', () => { ...@@ -35,28 +33,4 @@ describe('DurationChart getters', () => {
); );
}); });
}); });
describe('durationChartPlottableMedianData', () => {
it('returns plottable median data for selected stages', () => {
const stateWithDurationMedianData = {
durationMedianData: transformedDurationMedianData,
};
expect(
getters.durationChartMedianData(stateWithDurationMedianData, getters, rootState),
).toEqual(durationChartPlottableMedianData);
});
it('returns an empty array if there is no plottable median data for the selected stages', () => {
const stateWithDurationMedianData = {
startDate,
endDate,
durationMedianData: [],
};
expect(
getters.durationChartMedianData(stateWithDurationMedianData, getters, rootState),
).toEqual([]);
});
});
}); });
import mutations from 'ee/analytics/cycle_analytics/store/modules/duration_chart/mutations'; import mutations from 'ee/analytics/cycle_analytics/store/modules/duration_chart/mutations';
import * as types from 'ee/analytics/cycle_analytics/store/modules/duration_chart/mutation_types'; import * as types from 'ee/analytics/cycle_analytics/store/modules/duration_chart/mutation_types';
import { transformedDurationData, transformedDurationMedianData } from '../../../mock_data'; import { transformedDurationData } from '../../../mock_data';
let state = null; let state = null;
...@@ -26,7 +26,7 @@ describe('DurationChart mutations', () => { ...@@ -26,7 +26,7 @@ describe('DurationChart mutations', () => {
it.each` it.each`
mutation | payload | expectedState mutation | payload | expectedState
${types.UPDATE_SELECTED_DURATION_CHART_STAGES} | ${{ updatedDurationStageData: transformedDurationData, updatedDurationStageMedianData: transformedDurationMedianData }} | ${{ durationData: transformedDurationData, durationMedianData: transformedDurationMedianData }} ${types.UPDATE_SELECTED_DURATION_CHART_STAGES} | ${{ updatedDurationStageData: transformedDurationData }} | ${{ durationData: transformedDurationData }}
`( `(
'$mutation with payload $payload will update state with $expectedState', '$mutation with payload $payload will update state with $expectedState',
({ mutation, payload, expectedState }) => { ({ mutation, payload, expectedState }) => {
...@@ -52,31 +52,4 @@ describe('DurationChart mutations', () => { ...@@ -52,31 +52,4 @@ describe('DurationChart mutations', () => {
expect(stateWithData.durationData).toBe(transformedDurationData); expect(stateWithData.durationData).toBe(transformedDurationData);
}); });
}); });
describe(`${types.RECEIVE_DURATION_MEDIAN_DATA_SUCCESS}`, () => {
it('sets the data correctly', () => {
const stateWithData = {
durationMedianData: [['something', 'random']],
};
mutations[types.RECEIVE_DURATION_MEDIAN_DATA_SUCCESS](
stateWithData,
transformedDurationMedianData,
);
expect(stateWithData.durationMedianData).toBe(transformedDurationMedianData);
});
});
describe(`${types.RECEIVE_DURATION_MEDIAN_DATA_ERROR}`, () => {
it('sets durationMedianData to an empty array', () => {
const stateWithData = {
durationMedianData: [['something', 'random']],
};
mutations[types.RECEIVE_DURATION_MEDIAN_DATA_ERROR](stateWithData);
expect(stateWithData.durationMedianData).toStrictEqual([]);
});
});
}); });
...@@ -8,7 +8,6 @@ import { ...@@ -8,7 +8,6 @@ import {
getLabelEventsIdentifiers, getLabelEventsIdentifiers,
flattenDurationChartData, flattenDurationChartData,
getDurationChartData, getDurationChartData,
getDurationChartMedianData,
transformRawStages, transformRawStages,
isPersistedStage, isPersistedStage,
getTasksByTypeData, getTasksByTypeData,
...@@ -28,10 +27,8 @@ import { ...@@ -28,10 +27,8 @@ import {
labelStartEvent, labelStartEvent,
customStageStartEvents as startEvents, customStageStartEvents as startEvents,
transformedDurationData, transformedDurationData,
transformedDurationMedianData,
flattenedDurationData, flattenedDurationData,
durationChartPlottableData, durationChartPlottableData,
durationChartPlottableMedianData,
startDate, startDate,
endDate, endDate,
issueStage, issueStage,
...@@ -151,18 +148,6 @@ describe('Cycle analytics utils', () => { ...@@ -151,18 +148,6 @@ describe('Cycle analytics utils', () => {
}); });
}); });
describe('getDurationChartMedianData', () => {
it('computes the plottable data as expected', () => {
const plottableData = getDurationChartMedianData(
transformedDurationMedianData,
startDate,
endDate,
);
expect(plottableData).toStrictEqual(durationChartPlottableMedianData);
});
});
describe('transformRawStages', () => { describe('transformRawStages', () => {
it('retains all the stage properties', () => { it('retains all the stage properties', () => {
const transformed = transformRawStages([issueStage, rawCustomStage]); const transformed = transformRawStages([issueStage, rawCustomStage]);
......
...@@ -24992,9 +24992,6 @@ msgstr "" ...@@ -24992,9 +24992,6 @@ msgstr ""
msgid "There was an error while fetching value stream analytics duration data." msgid "There was an error while fetching value stream analytics duration data."
msgstr "" msgstr ""
msgid "There was an error while fetching value stream analytics duration median data."
msgstr ""
msgid "There was an error with the reCAPTCHA. Please solve the reCAPTCHA again." msgid "There was an error with the reCAPTCHA. Please solve the reCAPTCHA again."
msgstr "" msgstr ""
......
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