Commit 72ef8dfa authored by Kushal Pandya's avatar Kushal Pandya

Merge branch 'Remove-deprecated-epic-select-related-code-boards' into 'master'

Remove unused epic related boards code [RUN AS-IF-FOSS]

See merge request gitlab-org/gitlab!63272
parents 29fb851b 7018279b
#import "ee/graphql_shared/fragments/epic.fragment.graphql"
query Epic($fullPath: ID!, $iid: ID!) {
group(fullPath: $fullPath) {
epic(iid: $iid) {
...EpicNode
}
}
}
......@@ -19,10 +19,6 @@ fragment IssueNode on Issue {
relativePosition
epic {
id
iid
group {
fullPath
}
}
milestone {
id
......
#import "ee/graphql_shared/fragments/epic.fragment.graphql"
mutation issueSetEpic($input: IssueSetEpicInput!) {
issueSetEpic(input: $input) {
issue {
epic {
...EpicNode
}
}
errors
}
}
......@@ -27,14 +27,12 @@ import {
} from '../boards_util';
import { EpicFilterType, GroupByParamType, FilterFields } from '../constants';
import epicQuery from '../graphql/epic.query.graphql';
import createEpicBoardListMutation from '../graphql/epic_board_list_create.mutation.graphql';
import epicMoveListMutation from '../graphql/epic_move_list.mutation.graphql';
import epicsSwimlanesQuery from '../graphql/epics_swimlanes.query.graphql';
import groupBoardAssigneesQuery from '../graphql/group_board_assignees.query.graphql';
import groupBoardIterationsQuery from '../graphql/group_board_iterations.query.graphql';
import groupBoardMilestonesQuery from '../graphql/group_board_milestones.query.graphql';
import issueSetEpicMutation from '../graphql/issue_set_epic.mutation.graphql';
import issueSetWeightMutation from '../graphql/issue_set_weight.mutation.graphql';
import listUpdateLimitMetricsMutation from '../graphql/list_update_limit_metrics.mutation.graphql';
import listsEpicsQuery from '../graphql/lists_epics.query.graphql';
......@@ -163,7 +161,6 @@ export default {
epics: epicsFormatted,
canAdminEpic: epics.edges[0]?.node?.userPermissions?.adminEpic,
});
commit(types.UPDATE_CACHED_EPICS, epicsFormatted);
}
if (epics.pageInfo?.hasNextPage) {
......@@ -324,75 +321,6 @@ export default {
commit(types.RESET_EPICS);
},
fetchEpicForActiveIssue: async ({ state, commit, getters }) => {
if (!getters.activeBoardItem.epic) {
return false;
}
const {
epic: { id, iid, group: { fullPath } = {} },
} = getters.activeBoardItem;
if (!iid || !fullPath || state.epicsCacheById[id]) {
return false;
}
commit(types.SET_EPIC_FETCH_IN_PROGRESS, true);
try {
const {
data: {
group: { epic },
},
} = await gqlClient.query({
query: epicQuery,
variables: {
fullPath,
iid,
},
});
commit(types.UPDATE_CACHED_EPICS, [epic]);
} finally {
commit(types.SET_EPIC_FETCH_IN_PROGRESS, false);
}
return true;
},
setActiveIssueEpic: async ({ state, commit, getters }, epicId) => {
commit(types.SET_EPIC_FETCH_IN_PROGRESS, true);
const { data } = await gqlClient.mutate({
mutation: issueSetEpicMutation,
variables: {
input: {
iid: String(getters.activeBoardItem.iid),
epicId,
projectPath: getters.projectPathForActiveIssue,
},
},
});
if (data.issueSetEpic.errors?.length > 0) {
throw new Error(data.issueSetEpic.errors);
}
const { epic } = data.issueSetEpic.issue;
if (epic !== null) {
commit(types.RECEIVE_EPICS_SUCCESS, { epics: [epic, ...state.epics] });
commit(types.UPDATE_CACHED_EPICS, [epic]);
}
commit(typesCE.UPDATE_BOARD_ITEM_BY_ID, {
itemId: getters.activeBoardItem.id,
prop: 'epic',
value: epic ? { id: epic.id, iid: epic.iid, group: { fullPath: epic.group.fullPath } } : null,
});
commit(types.SET_EPIC_FETCH_IN_PROGRESS, false);
},
setActiveIssueWeight: async ({ commit, getters }, input) => {
const { data } = await gqlClient.mutate({
mutation: issueSetWeightMutation,
......
......@@ -9,8 +9,6 @@ export const RECEIVE_ISSUES_FOR_EPIC_FAILURE = 'RECEIVE_ISSUES_FOR_EPIC_FAILURE'
export const UPDATE_LIST_SUCCESS = 'UPDATE_LIST_SUCCESS';
export const RECEIVE_SWIMLANES_FAILURE = 'RECEIVE_SWIMLANES_FAILURE';
export const RECEIVE_EPICS_SUCCESS = 'RECEIVE_EPICS_SUCCESS';
export const UPDATE_CACHED_EPICS = 'UPDATE_CACHED_EPICS';
export const SET_EPIC_FETCH_IN_PROGRESS = 'SET_EPIC_FETCH_IN_PROGRESS';
export const RESET_EPICS = 'RESET_EPICS';
export const SET_SHOW_LABELS = 'SET_SHOW_LABELS';
export const MOVE_EPIC = 'MOVE_EPIC';
......
......@@ -92,16 +92,6 @@ export default {
}
},
[mutationTypes.UPDATE_CACHED_EPICS]: (state, epics) => {
epics.forEach((e) => {
Vue.set(state.epicsCacheById, e.id, e);
});
},
[mutationTypes.SET_EPIC_FETCH_IN_PROGRESS]: (state, val) => {
state.epicFetchInProgress = val;
},
[mutationTypes.RESET_EPICS]: (state) => {
Vue.set(state, 'epics', []);
},
......
......@@ -9,11 +9,7 @@ export default () => ({
epicLanesFetchInProgress: false,
listItemsFetchInProgress: false,
},
// The epic data stored in 'epics' do not always persist
// and will be cleared with changes to the filter.
epics: [],
epicsCacheById: {},
epicFetchInProgress: false,
milestones: [],
milestonesLoading: false,
iterations: [],
......
......@@ -240,23 +240,6 @@ export const mockEpic = {
labels: [],
};
export const mockEpic2 = {
id: 'gid://gitlab/Epic/42',
iid: '2',
group: { fullPath: 'gitlab-org' },
title: 'Epic title 2',
};
export const mockIssueWithEpic = {
...mockIssue3,
epic: {
id: mockEpic.id,
iid: mockEpic.iid,
webPath: '/gitlab-org/-/epics/41',
},
};
export const mockAssignedEpic = { ...mockIssueWithEpic.epic, title: mockEpic.title };
export const mockEpics = [
{
id: 'gid://gitlab/Epic/41',
......
......@@ -21,7 +21,6 @@ import {
mockIssue,
mockIssues,
mockEpic,
mockEpic2,
mockMilestones,
mockAssignees,
} from '../mock_data';
......@@ -216,7 +215,7 @@ describe('fetchEpicsSwimlanes', () => {
},
};
it('should commit mutation RECEIVE_EPICS_SUCCESS and UPDATE_CACHED_EPICS on success', (done) => {
it('should commit mutation RECEIVE_EPICS_SUCCESS on success', (done) => {
jest.spyOn(gqlClient, 'query').mockResolvedValue(queryResponse);
testAction(
......@@ -228,10 +227,6 @@ describe('fetchEpicsSwimlanes', () => {
type: types.RECEIVE_EPICS_SUCCESS,
payload: { epics: [mockEpic] },
},
{
type: types.UPDATE_CACHED_EPICS,
payload: [mockEpic],
},
],
[],
done,
......@@ -278,10 +273,6 @@ describe('fetchEpicsSwimlanes', () => {
type: types.RECEIVE_EPICS_SUCCESS,
payload: { epics: [mockEpic] },
},
{
type: types.UPDATE_CACHED_EPICS,
payload: [mockEpic],
},
],
[
{
......@@ -611,192 +602,6 @@ describe('resetEpics', () => {
});
});
describe('fetchEpicForActiveIssue', () => {
const assignedEpic = {
...mockIssue.epic,
};
describe("when active issue doesn't have an assigned epic", () => {
const getters = { activeBoardItem: { ...mockIssue, epic: null } };
it('should not fetch any epic', async () => {
await testAction(actions.fetchEpicForActiveIssue, undefined, { ...getters }, [], []);
});
});
describe("when active issue doesn't have the full epic information", () => {
// Edge Case: when user drops/moves a card onto an epic swimlane,
// until IssueMoveList request is completed, the issue item only has epic id.
// This causes a problem when user also has the sidebar open because
// board_sidebar_epic_select watches for the issue item's `epic` field
// and tries to extract epic id, epic iid and fullpath to request for detailed epic info.
const getters = { activeBoardItem: { ...mockIssue, epic: { id: 'something' } } };
it('should not fetch any epic', async () => {
await testAction(actions.fetchEpicForActiveIssue, undefined, { ...getters }, [], []);
});
});
describe('when the assigned epic for active issue is found in state.epicsCacheById', () => {
const getters = { activeBoardItem: { ...mockIssue, epic: assignedEpic } };
const state = { epicsCacheById: { [assignedEpic.id]: assignedEpic } };
it('should not fetch any epic', async () => {
await testAction(
actions.fetchEpicForActiveIssue,
undefined,
{ ...state, ...getters },
[],
[],
);
});
});
describe('when fetching fails', () => {
const getters = { activeBoardItem: { ...mockIssue, epic: assignedEpic } };
const state = { epicsCacheById: {} };
it('should not commit UPDATE_CACHED_EPICS mutation and should throw an error', () => {
const mockError = new Error('mayday');
jest.spyOn(gqlClient, 'query').mockRejectedValue(mockError);
return testAction(
actions.fetchEpicForActiveIssue,
undefined,
{ ...state, ...getters },
[
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: true,
},
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: false,
},
],
[],
).catch((e) => {
expect(e).toEqual(mockError);
});
});
});
describe("when the assigned epic for active issue isn't found in state.epicsCacheById", () => {
const getters = { activeBoardItem: { ...mockIssue, epic: assignedEpic } };
const state = { epicsCacheById: {} };
it('should commit mutation SET_EPIC_FETCH_IN_PROGRESS before and after committing mutation UPDATE_CACHED_EPICS', async () => {
jest.spyOn(gqlClient, 'query').mockResolvedValue({ data: { group: { epic: mockEpic } } });
await testAction(
actions.fetchEpicForActiveIssue,
undefined,
{ ...state, ...getters },
[
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: true,
},
{
type: types.UPDATE_CACHED_EPICS,
payload: [mockEpic],
},
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: false,
},
],
[],
);
});
});
});
describe('setActiveIssueEpic', () => {
const state = {
epics: [{ id: 'gid://gitlab/Epic/422', iid: 99, title: 'existing epic' }],
};
const getters = { activeBoardItem: { ...mockIssue, projectPath: 'h/b' } };
describe('when the updated issue has an assigned epic', () => {
it('should commit mutation RECEIVE_EPICS_SUCCESS, UPDATE_CACHED_EPICS and UPDATE_BOARD_ITEM_BY_ID on success', async () => {
jest
.spyOn(gqlClient, 'mutate')
.mockResolvedValue({ data: { issueSetEpic: { issue: { epic: mockEpic2 } } } });
await testAction(
actions.setActiveIssueEpic,
mockEpic2.id,
{ ...state, ...getters },
[
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: true,
},
{
type: types.RECEIVE_EPICS_SUCCESS,
payload: { epics: [mockEpic2, ...state.epics] },
},
{
type: types.UPDATE_CACHED_EPICS,
payload: [mockEpic2],
},
{
type: typesCE.UPDATE_BOARD_ITEM_BY_ID,
payload: {
itemId: mockIssue.id,
prop: 'epic',
value: { id: mockEpic2.id, iid: mockEpic2.iid, group: mockEpic2.group },
},
},
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: false,
},
],
[],
);
});
});
describe('when the updated issue does not have an epic (unassigned)', () => {
it('should only commit UPDATE_BOARD_ITEM_BY_ID on success', async () => {
jest
.spyOn(gqlClient, 'mutate')
.mockResolvedValue({ data: { issueSetEpic: { issue: { epic: null } } } });
await testAction(
actions.setActiveIssueEpic,
null,
{ ...state, ...getters },
[
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: true,
},
{
type: typesCE.UPDATE_BOARD_ITEM_BY_ID,
payload: { itemId: mockIssue.id, prop: 'epic', value: null },
},
{
type: types.SET_EPIC_FETCH_IN_PROGRESS,
payload: false,
},
],
[],
);
});
});
it('throws error if fails', async () => {
jest
.spyOn(gqlClient, 'mutate')
.mockResolvedValue({ data: { issueSetEpic: { errors: ['failed mutation'] } } });
await expect(actions.setActiveIssueEpic({ getters }, mockEpic2.id)).rejects.toThrow(Error);
});
});
describe('setActiveIssueWeight', () => {
const state = { boardItems: { [mockIssue.id]: mockIssue } };
const getters = { activeBoardItem: mockIssue };
......
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