Commit 3b0ffb54 authored by Phil Hughes's avatar Phil Hughes

Merge branch '31921-epic-sidebar-start-date-graphql' into 'master'

Use GraphQL mutation for epic date updates

Closes #31915 and #31921

See merge request gitlab-org/gitlab!22467
parents bd9f7eef fe03366a
mutation updateEpic($updateEpicInput: UpdateEpicInput!) {
updateEpic(input: $updateEpicInput) {
clientMutationId
errors
}
}
......@@ -7,6 +7,8 @@ import { visitUrl } from '~/lib/utils/url_utility';
import epicUtils from '../utils/epic_utils';
import { statusType, statusEvent, dateTypes } from '../constants';
import updateEpic from '../queries/updateEpic.mutation.graphql';
import * as types from './mutation_types';
export const setEpicMeta = ({ commit }, meta) => commit(types.SET_EPIC_META, meta);
......@@ -125,23 +127,35 @@ export const requestEpicDateSaveFailure = ({ commit }, data) => {
);
};
export const saveDate = ({ state, dispatch }, { dateType, dateTypeIsFixed, newDate }) => {
const requestBody = {
[dateType === dateTypes.start ? 'start_date_is_fixed' : 'due_date_is_fixed']: dateTypeIsFixed,
const updateEpicInput = {
iid: `${state.epicId}`,
groupPath: state.groupPath,
[dateType === dateTypes.start ? 'startDateIsFixed' : 'dueDateIsFixed']: dateTypeIsFixed,
};
if (dateTypeIsFixed) {
requestBody[dateType === dateTypes.start ? 'start_date_fixed' : 'due_date_fixed'] = newDate;
updateEpicInput[dateType === dateTypes.start ? 'startDateFixed' : 'dueDateFixed'] = newDate;
}
dispatch('requestEpicDateSave', { dateType });
axios
.put(state.endpoint, requestBody)
.then(() => {
dispatch('requestEpicDateSaveSuccess', {
dateType,
dateTypeIsFixed,
newDate,
});
epicUtils.gqClient
.mutate({
mutation: updateEpic,
variables: {
updateEpicInput,
},
})
.then(({ data }) => {
if (!data?.updateEpic?.errors.length) {
dispatch('requestEpicDateSaveSuccess', {
dateType,
dateTypeIsFixed,
newDate,
});
} else {
// eslint-disable-next-line @gitlab/i18n/no-non-i18n-strings
throw new Error('An error occurred while saving the date');
}
})
.catch(() => {
dispatch('requestEpicDateSaveFailure', {
......
......@@ -3,11 +3,14 @@ import Cookies from 'js-cookie';
import { __, s__, sprintf } from '~/locale';
import createGqClient from '~/lib/graphql';
import { parseBoolean } from '~/lib/utils/common_utils';
import { dateInWords, parsePikadayDate } from '~/lib/utils/datetime_utility';
import { dateTypes } from '../constants';
const gqClient = createGqClient();
const triggerDocumentEvent = (eventName, eventParam) => {
$(document).trigger(eventName, eventParam);
};
......@@ -90,6 +93,7 @@ const getDateFromMilestonesTooltip = ({
// be default export of dependency as per
// https://gitlab.com/help/development/testing_guide/frontend_testing.md#stubbing-and-mocking
const epicUtils = {
gqClient,
triggerDocumentEvent,
bindDocumentEvent,
toggleContainerClass,
......
......@@ -605,6 +605,14 @@ describe('Epic Store Actions', () => {
describe('saveDate', () => {
let mock;
const mockUpdateEpicMutationRes = {
updateEpic: {
clientMutationId: null,
errors: [],
__typename: 'UpdateEpicPayload',
},
};
const data = {
dateType: dateTypes.start,
dateTypeIsFixed: true,
......@@ -621,6 +629,11 @@ describe('Epic Store Actions', () => {
it('dispatches requestEpicDateSave and requestEpicDateSaveSuccess when request is successful', done => {
mock.onPut(/(.*)/).replyOnce(200, {});
spyOn(epicUtils.gqClient, 'mutate').and.returnValue(
Promise.resolve({
data: mockUpdateEpicMutationRes,
}),
);
testAction(
actions.saveDate,
......@@ -643,6 +656,16 @@ describe('Epic Store Actions', () => {
it('dispatches requestEpicDateSave and requestEpicDateSaveFailure when request fails', done => {
mock.onPut(/(.*)/).replyOnce(500, {});
spyOn(epicUtils.gqClient, 'mutate').and.returnValue(
Promise.resolve({
data: {
updateEpic: {
...mockUpdateEpicMutationRes,
errors: [{ foo: 'bar' }],
},
},
}),
);
testAction(
actions.saveDate,
......@@ -662,54 +685,6 @@ describe('Epic Store Actions', () => {
done,
);
});
it('calls `axios.put` with request body containing start date related payload when called with `dateType` as `start`', () => {
spyOn(axios, 'put').and.callFake(() => new Promise(() => {}));
actions.saveDate(
{
state: { endpoint: '/foo/bar' },
dispatch: () => {},
},
{
dateType: dateTypes.start,
newDate: '2018-1-1',
dateTypeIsFixed: true,
},
);
expect(axios.put).toHaveBeenCalledWith(
'/foo/bar',
jasmine.objectContaining({
start_date_is_fixed: true,
start_date_fixed: '2018-1-1',
}),
);
});
it('calls `axios.put` with request body containing due date related payload when called with `dateType` as `due`', () => {
spyOn(axios, 'put').and.callFake(() => new Promise(() => {}));
actions.saveDate(
{
state: { endpoint: '/foo/bar' },
dispatch: () => {},
},
{
dateType: dateTypes.due,
newDate: '2018-1-1',
dateTypeIsFixed: true,
},
);
expect(axios.put).toHaveBeenCalledWith(
'/foo/bar',
jasmine.objectContaining({
due_date_is_fixed: true,
due_date_fixed: '2018-1-1',
}),
);
});
});
describe('requestEpicSubscriptionToggle', () => {
......
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