Commit b600e106 authored by Kushal Pandya's avatar Kushal Pandya

Merge branch 'update-roadmap-graphql-mock-data' into 'master'

Update mock data and fix vacuous group id check in epic roadmap

See merge request gitlab-org/gitlab!56922
parents 8c94271e e46aa19a
<script> <script>
import { GlButton, GlIcon, GlLoadingIcon, GlTooltip } from '@gitlab/ui'; import { GlButton, GlIcon, GlLoadingIcon, GlTooltip } from '@gitlab/ui';
import { mapState } from 'vuex'; import { mapState } from 'vuex';
import { getIdFromGraphQLId } from '~/graphql_shared/utils';
import { __, n__ } from '~/locale'; import { __, n__ } from '~/locale';
import { EPIC_LEVEL_MARGIN } from '../constants'; import { EPIC_LEVEL_MARGIN } from '../constants';
import eventHub from '../event_hub'; import eventHub from '../event_hub';
...@@ -48,8 +49,11 @@ export default { ...@@ -48,8 +49,11 @@ export default {
itemId() { itemId() {
return this.epic.id; return this.epic.id;
}, },
epicGroupId() {
return getIdFromGraphQLId(this.epic.group.id);
},
isEpicGroupDifferent() { isEpicGroupDifferent() {
return this.currentGroupId !== this.epic.groupId; return this.currentGroupId !== this.epicGroupId;
}, },
isExpandIconHidden() { isExpandIconHidden() {
return !this.epic.hasChildren; return !this.epic.hasChildren;
...@@ -147,10 +151,10 @@ export default { ...@@ -147,10 +151,10 @@ export default {
<div class="epic-group-timeframe d-flex text-secondary"> <div class="epic-group-timeframe d-flex text-secondary">
<span <span
v-if="isEpicGroupDifferent && !epic.hasParent" v-if="isEpicGroupDifferent && !epic.hasParent"
:title="epic.groupFullName" :title="epic.group.fullName"
class="epic-group" class="epic-group"
> >
{{ epic.groupName }} {{ epic.group.name }}
</span> </span>
<span v-if="isEpicGroupDifferent && !epic.hasParent" class="mx-1" aria-hidden="true" <span v-if="isEpicGroupDifferent && !epic.hasParent" class="mx-1" aria-hidden="true"
>&middot;</span >&middot;</span
......
...@@ -19,6 +19,7 @@ fragment BaseEpic on Epic { ...@@ -19,6 +19,7 @@ fragment BaseEpic on Epic {
closedEpics closedEpics
} }
group { group {
id
name name
fullName fullName
fullPath fullPath
......
...@@ -57,7 +57,7 @@ const fetchGroupEpics = ( ...@@ -57,7 +57,7 @@ const fetchGroupEpics = (
? data?.group?.epic?.children?.edges || [] ? data?.group?.epic?.children?.edges || []
: data?.group?.epics?.edges || []; : data?.group?.epics?.edges || [];
return epicUtils.extractGroupEpics(edges); return edges.map((e) => e.node);
}); });
}; };
...@@ -72,7 +72,7 @@ export const fetchChildrenEpics = (state, { parentItem }) => { ...@@ -72,7 +72,7 @@ export const fetchChildrenEpics = (state, { parentItem }) => {
}) })
.then(({ data }) => { .then(({ data }) => {
const edges = data?.group?.epic?.children?.edges || []; const edges = data?.group?.epic?.children?.edges || [];
return epicUtils.extractGroupEpics(edges); return edges.map((e) => e.node);
}); });
}; };
......
...@@ -7,23 +7,6 @@ export const gqClient = createGqClient( ...@@ -7,23 +7,6 @@ export const gqClient = createGqClient(
}, },
); );
export const flattenGroupProperty = ({ node: epicNode }) => ({
...epicNode,
// We can get rid of below two lines
// by updating `epic_item_details.vue`
// once we move to GraphQL permanently.
groupName: epicNode.group.name,
groupFullName: epicNode.group.fullName,
});
/**
* Returns array of epics extracted from GraphQL response
* discarding the `edges`->`node` nesting
*
* @param {Object} edges
*/
export const extractGroupEpics = (edges) => edges.map(flattenGroupProperty);
export const addIsChildEpicTrueProperty = (obj) => ({ ...obj, isChildEpic: true }); export const addIsChildEpicTrueProperty = (obj) => ({ ...obj, isChildEpic: true });
export const generateKey = (epic) => `${epic.isChildEpic ? 'child-epic-' : 'epic-'}${epic.id}`; export const generateKey = (epic) => `${epic.isChildEpic ? 'child-epic-' : 'epic-'}${epic.id}`;
...@@ -31,7 +31,7 @@ describe('EpicItemDetails', () => { ...@@ -31,7 +31,7 @@ describe('EpicItemDetails', () => {
currentGroupId: mockGroupId, currentGroupId: mockGroupId,
timeframeString: 'Jul 10, 2017 – Jun 2, 2018', timeframeString: 'Jul 10, 2017 – Jun 2, 2018',
childLevel: 0, childLevel: 0,
childrenFlags: { 41: { itemExpanded: false } }, childrenFlags: { [mockFormattedEpic.id]: { itemExpanded: false } },
hasFiltersApplied: false, hasFiltersApplied: false,
isChildrenEmpty: false, isChildrenEmpty: false,
...props, ...props,
...@@ -88,31 +88,19 @@ describe('EpicItemDetails', () => { ...@@ -88,31 +88,19 @@ describe('EpicItemDetails', () => {
}); });
describe('epic group name', () => { describe('epic group name', () => {
const epic = {
id: '41',
...mockFormattedEpic,
groupId: 1,
groupName: 'Bar',
groupFullName: 'Foo / Bar',
descendantCounts: {
closedIssues: 3,
openedIssues: 2,
},
};
describe('when the epic group ID is different from the current group ID', () => { describe('when the epic group ID is different from the current group ID', () => {
it('is displayed and set to the title attribute', () => { it('is displayed and set to the title attribute', () => {
createWrapper({ epic, currentGroupId: 2 }); createWrapper({ currentGroupId: 123 });
expect(getEpicGroupNameData()).toEqual({ expect(getEpicGroupNameData()).toEqual({
groupName: epic.groupName, groupName: mockFormattedEpic.group.name,
title: epic.groupFullName, title: mockFormattedEpic.group.fullName,
}); });
}); });
}); });
describe('when the epic group ID is the same as the current group ID', () => { describe('when the epic group ID is the same as the current group ID', () => {
it('is hidden', () => { it('is hidden', () => {
createWrapper({ epic, currentGroupId: 1 }); createWrapper({ currentGroupId: mockGroupId });
expect(getGroupName().exists()).toBe(false); expect(getGroupName().exists()).toBe(false);
}); });
}); });
...@@ -178,7 +166,6 @@ describe('EpicItemDetails', () => { ...@@ -178,7 +166,6 @@ describe('EpicItemDetails', () => {
let epic; let epic;
beforeEach(() => { beforeEach(() => {
epic = createMockEpic({ epic = createMockEpic({
id: 41,
hasChildren: true, hasChildren: true,
children: { children: {
edges: [mockFormattedChildEpic1], edges: [mockFormattedChildEpic1],
...@@ -203,7 +190,7 @@ describe('EpicItemDetails', () => { ...@@ -203,7 +190,7 @@ describe('EpicItemDetails', () => {
describe('when child epics are expanded', () => { describe('when child epics are expanded', () => {
const childrenFlags = { const childrenFlags = {
41: { itemExpanded: true }, [mockFormattedEpic.id]: { itemExpanded: true },
}; };
beforeEach(() => { beforeEach(() => {
...@@ -241,7 +228,7 @@ describe('EpicItemDetails', () => { ...@@ -241,7 +228,7 @@ describe('EpicItemDetails', () => {
describe('when child epics are not expanded', () => { describe('when child epics are not expanded', () => {
beforeEach(() => { beforeEach(() => {
const childrenFlags = { const childrenFlags = {
41: { itemExpanded: false }, [mockFormattedEpic.id]: { itemExpanded: false },
}; };
createWrapper({ createWrapper({
epic, epic,
......
...@@ -36,7 +36,7 @@ const createComponent = ({ ...@@ -36,7 +36,7 @@ const createComponent = ({
currentGroupId = mockGroupId, currentGroupId = mockGroupId,
childLevel = 0, childLevel = 0,
childrenEpics = {}, childrenEpics = {},
childrenFlags = { 1: { itemExpanded: false } }, childrenFlags = { [mockEpic.id]: { itemExpanded: false } },
hasFiltersApplied = false, hasFiltersApplied = false,
}) => { }) => {
return mount(EpicItemComponent, { return mount(EpicItemComponent, {
......
...@@ -18,7 +18,6 @@ import { ...@@ -18,7 +18,6 @@ import {
mockEpicsWithParents, mockEpicsWithParents,
mockSortedBy, mockSortedBy,
basePath, basePath,
epicsPath,
} from 'ee_jest/roadmap/mock_data'; } from 'ee_jest/roadmap/mock_data';
const mockTimeframeMonths = getTimeframeForMonthsView(mockTimeframeInitialDate); const mockTimeframeMonths = getTimeframeForMonthsView(mockTimeframeInitialDate);
...@@ -29,7 +28,6 @@ store.dispatch('setInitialData', { ...@@ -29,7 +28,6 @@ store.dispatch('setInitialData', {
presetType: PRESET_TYPES.MONTHS, presetType: PRESET_TYPES.MONTHS,
timeframe: mockTimeframeMonths, timeframe: mockTimeframeMonths,
filterQueryString: '', filterQueryString: '',
initialEpicsPath: epicsPath,
basePath, basePath,
}); });
......
...@@ -9,7 +9,11 @@ import { ...@@ -9,7 +9,11 @@ import {
} from 'ee/roadmap/constants'; } from 'ee/roadmap/constants';
import createStore from 'ee/roadmap/store'; import createStore from 'ee/roadmap/store';
import { getTimeframeForMonthsView } from 'ee/roadmap/utils/roadmap_utils'; import { getTimeframeForMonthsView } from 'ee/roadmap/utils/roadmap_utils';
import { mockTimeframeInitialDate, mockGroupId, rawMilestones } from 'ee_jest/roadmap/mock_data'; import {
mockTimeframeInitialDate,
mockGroupId,
mockGroupMilestones,
} from 'ee_jest/roadmap/mock_data';
import { createMockDirective, getBinding } from 'helpers/vue_mock_directive'; import { createMockDirective, getBinding } from 'helpers/vue_mock_directive';
const initializeStore = (mockTimeframeMonths) => { const initializeStore = (mockTimeframeMonths) => {
...@@ -19,7 +23,7 @@ const initializeStore = (mockTimeframeMonths) => { ...@@ -19,7 +23,7 @@ const initializeStore = (mockTimeframeMonths) => {
presetType: PRESET_TYPES.MONTHS, presetType: PRESET_TYPES.MONTHS,
timeframe: mockTimeframeMonths, timeframe: mockTimeframeMonths,
}); });
store.dispatch('receiveMilestonesSuccess', { rawMilestones }); store.dispatch('receiveMilestonesSuccess', { rawMilestones: mockGroupMilestones });
return store; return store;
}; };
......
...@@ -13,7 +13,6 @@ import * as types from 'ee/roadmap/store/mutation_types'; ...@@ -13,7 +13,6 @@ import * as types from 'ee/roadmap/store/mutation_types';
import { getTimeframeForMonthsView } from 'ee/roadmap/utils/roadmap_utils'; import { getTimeframeForMonthsView } from 'ee/roadmap/utils/roadmap_utils';
import { import {
basePath, basePath,
epicsPath,
mockFormattedEpic, mockFormattedEpic,
mockFormattedChildEpic2, mockFormattedChildEpic2,
mockGroupId, mockGroupId,
...@@ -62,7 +61,6 @@ describe('RoadmapApp', () => { ...@@ -62,7 +61,6 @@ describe('RoadmapApp', () => {
timeframe, timeframe,
hasFiltersApplied, hasFiltersApplied,
filterQueryString: '', filterQueryString: '',
initialEpicsPath: epicsPath,
basePath, basePath,
}); });
}); });
......
This diff is collapsed.
...@@ -13,19 +13,21 @@ import axios from '~/lib/utils/axios_utils'; ...@@ -13,19 +13,21 @@ import axios from '~/lib/utils/axios_utils';
import { import {
mockGroupId, mockGroupId,
basePath, basePath,
epicsPath,
mockTimeframeInitialDate, mockTimeframeInitialDate,
mockTimeframeMonthsPrepend, mockTimeframeMonthsPrepend,
mockTimeframeMonthsAppend, mockTimeframeMonthsAppend,
rawEpics, rawEpics,
mockRawEpic, mockRawEpic,
mockRawEpic2,
mockFormattedEpic, mockFormattedEpic,
mockFormattedEpic2,
mockSortedBy, mockSortedBy,
mockGroupEpicsQueryResponse, mockGroupEpicsQueryResponse,
mockGroupEpicsQueryResponseFormatted, mockGroupEpics,
mockGroupMilestonesQueryResponse,
mockEpicChildEpicsQueryResponse, mockEpicChildEpicsQueryResponse,
rawMilestones, mockChildEpicNode1,
mockGroupMilestonesQueryResponse,
mockGroupMilestones,
mockMilestone, mockMilestone,
mockFormattedMilestone, mockFormattedMilestone,
} from '../mock_data'; } from '../mock_data';
...@@ -46,7 +48,6 @@ describe('Roadmap Vuex Actions', () => { ...@@ -46,7 +48,6 @@ describe('Roadmap Vuex Actions', () => {
timeframe: mockTimeframeMonths, timeframe: mockTimeframeMonths,
presetType: PRESET_TYPES.MONTHS, presetType: PRESET_TYPES.MONTHS,
sortedBy: mockSortedBy, sortedBy: mockSortedBy,
initialEpicsPath: epicsPath,
filterQueryString: '', filterQueryString: '',
basePath, basePath,
timeframeStartDate, timeframeStartDate,
...@@ -76,55 +77,21 @@ describe('Roadmap Vuex Actions', () => { ...@@ -76,55 +77,21 @@ describe('Roadmap Vuex Actions', () => {
return testAction( return testAction(
actions.receiveEpicsSuccess, actions.receiveEpicsSuccess,
{ {
rawEpics: [ rawEpics: [mockRawEpic2],
{
...mockRawEpic,
start_date: '2017-12-31',
end_date: '2018-2-15',
descendantWeightSum: {
closedIssues: 3,
openedIssues: 2,
},
descendantCounts: {
openedEpics: 3,
closedEpics: 2,
},
},
],
}, },
state, state,
[ [
{ type: types.UPDATE_EPIC_IDS, payload: [mockRawEpic.id] }, { type: types.UPDATE_EPIC_IDS, payload: [mockRawEpic2.id] },
{ {
type: types.RECEIVE_EPICS_SUCCESS, type: types.RECEIVE_EPICS_SUCCESS,
payload: [ payload: [mockFormattedEpic2],
{
...mockFormattedEpic,
startDateOutOfRange: false,
endDateOutOfRange: false,
startDate: new Date(2017, 11, 31),
originalStartDate: new Date(2017, 11, 31),
endDate: new Date(2018, 1, 15),
originalEndDate: new Date(2018, 1, 15),
},
],
}, },
], ],
[ [
{ {
type: 'initItemChildrenFlags', type: 'initItemChildrenFlags',
payload: { payload: {
epics: [ epics: [mockFormattedEpic2],
{
...mockFormattedEpic,
startDateOutOfRange: false,
endDateOutOfRange: false,
startDate: new Date(2017, 11, 31),
originalStartDate: new Date(2017, 11, 31),
endDate: new Date(2018, 1, 15),
originalEndDate: new Date(2018, 1, 15),
},
],
}, },
}, },
], ],
...@@ -135,15 +102,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -135,15 +102,7 @@ describe('Roadmap Vuex Actions', () => {
return testAction( return testAction(
actions.receiveEpicsSuccess, actions.receiveEpicsSuccess,
{ {
rawEpics: [ rawEpics: [mockRawEpic],
{
...mockRawEpic,
descendantWeightSum: {
closedIssues: 3,
openedIssues: 2,
},
},
],
newEpic: true, newEpic: true,
timeframeExtended: true, timeframeExtended: true,
}, },
...@@ -162,9 +121,9 @@ describe('Roadmap Vuex Actions', () => { ...@@ -162,9 +121,9 @@ describe('Roadmap Vuex Actions', () => {
epics: [ epics: [
{ {
...mockFormattedEpic, ...mockFormattedEpic,
newEpic: true,
startDateOutOfRange: true, startDateOutOfRange: true,
endDateOutOfRange: false, endDateOutOfRange: false,
newEpic: true,
}, },
], ],
}, },
...@@ -223,7 +182,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -223,7 +182,7 @@ describe('Roadmap Vuex Actions', () => {
[ [
{ {
type: 'receiveEpicsSuccess', type: 'receiveEpicsSuccess',
payload: { rawEpics: mockGroupEpicsQueryResponseFormatted }, payload: { rawEpics: mockGroupEpics },
}, },
], ],
); );
...@@ -275,7 +234,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -275,7 +234,7 @@ describe('Roadmap Vuex Actions', () => {
{ {
type: 'receiveEpicsSuccess', type: 'receiveEpicsSuccess',
payload: { payload: {
rawEpics: mockGroupEpicsQueryResponseFormatted, rawEpics: mockGroupEpics,
newEpic: true, newEpic: true,
timeframeExtended: true, timeframeExtended: true,
}, },
...@@ -369,21 +328,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -369,21 +328,7 @@ describe('Roadmap Vuex Actions', () => {
actions.receiveChildrenSuccess, actions.receiveChildrenSuccess,
{ {
parentItemId: '41', parentItemId: '41',
rawChildren: [ rawChildren: [mockRawEpic2],
{
...mockRawEpic,
start_date: '2017-12-31',
end_date: '2018-2-15',
descendantWeightSum: {
closedIssues: 3,
openedIssues: 2,
},
descendantCounts: {
openedEpics: 3,
closedEpics: 2,
},
},
],
}, },
state, state,
[ [
...@@ -393,13 +338,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -393,13 +338,7 @@ describe('Roadmap Vuex Actions', () => {
parentItemId: '41', parentItemId: '41',
children: [ children: [
{ {
...mockFormattedEpic, ...mockFormattedEpic2,
startDateOutOfRange: false,
endDateOutOfRange: false,
startDate: new Date(2017, 11, 31),
originalStartDate: new Date(2017, 11, 31),
endDate: new Date(2018, 1, 15),
originalEndDate: new Date(2018, 1, 15),
isChildEpic: true, isChildEpic: true,
}, },
], ],
...@@ -416,13 +355,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -416,13 +355,7 @@ describe('Roadmap Vuex Actions', () => {
payload: { payload: {
epics: [ epics: [
{ {
...mockFormattedEpic, ...mockFormattedEpic2,
startDateOutOfRange: false,
endDateOutOfRange: false,
startDate: new Date(2017, 11, 31),
originalStartDate: new Date(2017, 11, 31),
endDate: new Date(2018, 1, 15),
originalEndDate: new Date(2018, 1, 15),
isChildEpic: true, isChildEpic: true,
}, },
], ],
...@@ -504,10 +437,6 @@ describe('Roadmap Vuex Actions', () => { ...@@ -504,10 +437,6 @@ describe('Roadmap Vuex Actions', () => {
itemExpanded: false, itemExpanded: false,
}; };
const children = epicUtils.extractGroupEpics(
mockEpicChildEpicsQueryResponse.data.group.epic.children.edges,
);
testAction( testAction(
actions.toggleEpic, actions.toggleEpic,
{ parentItem }, { parentItem },
...@@ -522,7 +451,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -522,7 +451,7 @@ describe('Roadmap Vuex Actions', () => {
type: 'receiveChildrenSuccess', type: 'receiveChildrenSuccess',
payload: { payload: {
parentItemId: parentItem.id, parentItemId: parentItem.id,
rawChildren: children, rawChildren: [mockChildEpicNode1],
}, },
}, },
], ],
...@@ -668,7 +597,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -668,7 +597,7 @@ describe('Roadmap Vuex Actions', () => {
}, },
{ {
type: 'receiveMilestonesSuccess', type: 'receiveMilestonesSuccess',
payload: { rawMilestones }, payload: { rawMilestones: mockGroupMilestones },
}, },
], ],
); );
...@@ -747,7 +676,7 @@ describe('Roadmap Vuex Actions', () => { ...@@ -747,7 +676,7 @@ describe('Roadmap Vuex Actions', () => {
describe('refreshMilestoneDates', () => { describe('refreshMilestoneDates', () => {
it('should update milestones after refreshing milestone dates to match with updated timeframe', () => { it('should update milestones after refreshing milestone dates to match with updated timeframe', () => {
const milestones = rawMilestones.map((milestone) => const milestones = mockGroupMilestones.map((milestone) =>
roadmapItemUtils.formatRoadmapItemDetails( roadmapItemUtils.formatRoadmapItemDetails(
milestone, milestone,
state.timeframeStartDate, state.timeframeStartDate,
......
...@@ -3,13 +3,7 @@ import mutations from 'ee/roadmap/store/mutations'; ...@@ -3,13 +3,7 @@ import mutations from 'ee/roadmap/store/mutations';
import defaultState from 'ee/roadmap/store/state'; import defaultState from 'ee/roadmap/store/state';
import { import { mockGroupId, basePath, mockSortedBy, mockEpic } from 'ee_jest/roadmap/mock_data';
mockGroupId,
basePath,
epicsPath,
mockSortedBy,
mockEpic,
} from 'ee_jest/roadmap/mock_data';
const setEpicMockData = (state) => { const setEpicMockData = (state) => {
state.epics = [mockEpic]; state.epics = [mockEpic];
...@@ -33,7 +27,6 @@ describe('Roadmap Store Mutations', () => { ...@@ -33,7 +27,6 @@ describe('Roadmap Store Mutations', () => {
epicsFetchResultEmpty: false, epicsFetchResultEmpty: false,
currentGroupId: mockGroupId, currentGroupId: mockGroupId,
sortedBy: mockSortedBy, sortedBy: mockSortedBy,
initialEpicsPath: epicsPath,
defaultInnerHeight: 600, defaultInnerHeight: 600,
extendedTimeframe: [], extendedTimeframe: [],
filterQueryString: '', filterQueryString: '',
......
import * as epicUtils from 'ee/roadmap/utils/epic_utils'; import * as epicUtils from 'ee/roadmap/utils/epic_utils';
import { mockGroupEpicsQueryResponse } from '../mock_data';
describe('extractGroupEpics', () => {
it('returns array of epics with `edges->nodes` nesting removed', () => {
const { edges } = mockGroupEpicsQueryResponse.data.group.epics;
const extractedEpics = epicUtils.extractGroupEpics(edges);
expect(extractedEpics).toHaveLength(edges.length);
expect(extractedEpics[0]).toEqual(
expect.objectContaining({
...edges[0].node,
groupName: edges[0].node.group.name,
groupFullName: edges[0].node.group.fullName,
}),
);
});
});
describe('addIsChildEpicTrueProperty', () => { describe('addIsChildEpicTrueProperty', () => {
const title = 'Lorem ipsum dolar sit'; const title = 'Lorem ipsum dolar sit';
const description = 'Beatae suscipit dolorum nihil quidem est accusamus'; const description = 'Beatae suscipit dolorum nihil quidem est accusamus';
......
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