diff options
Diffstat (limited to 'spec/frontend/users_select/test_helper.js')
-rw-r--r-- | spec/frontend/users_select/test_helper.js | 152 |
1 files changed, 152 insertions, 0 deletions
diff --git a/spec/frontend/users_select/test_helper.js b/spec/frontend/users_select/test_helper.js new file mode 100644 index 00000000000..c5adbe9bb09 --- /dev/null +++ b/spec/frontend/users_select/test_helper.js @@ -0,0 +1,152 @@ +import MockAdapter from 'axios-mock-adapter'; +import { memoize, cloneDeep } from 'lodash'; +import { getFixture, getJSONFixture } from 'helpers/fixtures'; +import waitForPromises from 'helpers/wait_for_promises'; +import axios from '~/lib/utils/axios_utils'; +import UsersSelect from '~/users_select'; + +// fixtures ------------------------------------------------------------------- +const getUserSearchHTML = memoize((fixturePath) => { + const html = getFixture(fixturePath); + const parser = new DOMParser(); + + const el = parser.parseFromString(html, 'text/html').querySelector('.assignee'); + + return el.outerHTML; +}); + +const getUsersFixture = memoize(() => getJSONFixture('autocomplete/users.json')); + +export const getUsersFixtureAt = (idx) => getUsersFixture()[idx]; + +// test context --------------------------------------------------------------- +export const createTestContext = ({ fixturePath }) => { + let mock = null; + let subject = null; + + const setup = () => { + const rootEl = document.createElement('div'); + rootEl.innerHTML = getUserSearchHTML(fixturePath); + document.body.appendChild(rootEl); + + mock = new MockAdapter(axios); + mock.onGet('/-/autocomplete/users.json').reply(200, cloneDeep(getUsersFixture())); + }; + + const teardown = () => { + mock.restore(); + document.body.innerHTML = ''; + subject = null; + }; + + const createSubject = () => { + if (subject) { + throw new Error('test subject is already created'); + } + + subject = new UsersSelect(null); + }; + + return { + setup, + teardown, + createSubject, + }; +}; + +// finders ------------------------------------------------------------------- +export const findAssigneesInputs = () => + document.querySelectorAll('input[name="merge_request[assignee_ids][]'); +export const findAssigneesInputsModel = () => + Array.from(findAssigneesInputs()).map((input) => ({ + value: input.value, + dataset: { ...input.dataset }, + })); +export const findUserSearchButton = () => document.querySelector('.js-user-search'); +export const findDropdownItem = ({ id }) => document.querySelector(`li[data-user-id="${id}"] a`); +export const findDropdownItemsModel = () => + Array.from(document.querySelectorAll('.dropdown-content li')).map((el) => { + if (el.classList.contains('divider')) { + return { + type: 'divider', + }; + } else if (el.classList.contains('dropdown-header')) { + return { + type: 'dropdown-header', + text: el.textContent, + }; + } + + return { + type: 'user', + userId: el.dataset.userId, + }; + }); + +// arrange/act helpers ------------------------------------------------------- +export const setAssignees = (...users) => { + findAssigneesInputs().forEach((x) => x.remove()); + + const container = document.querySelector('.js-sidebar-assignee-data'); + + container.prepend( + ...users.map((user) => { + const input = document.createElement('input'); + input.name = 'merge_request[assignee_ids][]'; + input.value = user.id.toString(); + input.setAttribute('data-avatar-url', user.avatar_url); + input.setAttribute('data-name', user.name); + input.setAttribute('data-username', user.username); + input.setAttribute('data-can-merge', user.can_merge); + return input; + }), + ); +}; +export const toggleDropdown = () => findUserSearchButton().click(); +export const waitForDropdownItems = async () => { + await axios.waitForAll(); + await waitForPromises(); +}; + +// assertion helpers --------------------------------------------------------- +export const createUnassignedExpectation = () => { + return [ + { type: 'user', userId: '0' }, + { type: 'divider' }, + ...getUsersFixture().map((x) => ({ + type: 'user', + userId: x.id.toString(), + })), + ]; +}; + +export const createAssignedExpectation = ({ header, assigned }) => { + const assignedIds = new Set(assigned.map((x) => x.id)); + const unassignedIds = getUsersFixture().filter((x) => !assignedIds.has(x.id)); + + return [ + { type: 'user', userId: '0' }, + { type: 'divider' }, + { type: 'dropdown-header', text: header }, + ...assigned.map((x) => ({ type: 'user', userId: x.id.toString() })), + { type: 'divider' }, + ...unassignedIds.map((x) => ({ type: 'user', userId: x.id.toString() })), + ]; +}; + +export const createInputsModelExpectation = (users) => + users.map((user) => ({ + value: user.id.toString(), + dataset: { + approved: user.approved.toString(), + avatar_url: user.avatar_url, + can_merge: user.can_merge.toString(), + can_update_merge_request: user.can_update_merge_request.toString(), + id: user.id.toString(), + name: user.name, + show_status: user.show_status.toString(), + state: user.state, + username: user.username, + web_url: user.web_url, + }, + })); |