diff options
author | Sarah German <sgerman@gitlab.com> | 2022-07-25 23:22:16 +0300 |
---|---|---|
committer | Sarah German <sgerman@gitlab.com> | 2022-07-25 23:22:16 +0300 |
commit | efcba26710ede46cdaf6e260462eb2d19238ba13 (patch) | |
tree | 1001ca1595db1985df815807ecc1e71b575ee2ad | |
parent | eee87da334561ee694eaeb8e0720ee45c99d84f8 (diff) |
Ensure correct paths for Versions menu linksversions-links
3 files changed, 91 insertions, 7 deletions
diff --git a/content/frontend/default/components/versions_menu.vue b/content/frontend/default/components/versions_menu.vue index 04d2b982..c2ed5235 100644 --- a/content/frontend/default/components/versions_menu.vue +++ b/content/frontend/default/components/versions_menu.vue @@ -30,6 +30,14 @@ export default { methods: { getVersionPath(versionNumber) { let path = window.location.pathname; + + // If we're viewing an older version, drop its version prefix when creating links. + if (this.activeVersion !== this.versions.next) { + const pathArr = window.location.pathname.split('/').filter((n) => n); + pathArr.shift(); + path = `/${pathArr.join('/')}`; + } + if (versionNumber) { path = `/${versionNumber}${path}`; } @@ -41,9 +49,11 @@ export default { // Check if the first item in the URL path is a valid version. // If so, that should be the active menu item. const versionPath = window.location.pathname.split('/')[1]; - if (Object.values(this.versions).includes(versionPath)) { - activeVersion = versionPath; - } + Object.keys(versions).forEach((key) => { + if (versions[key] === versionPath || versions[key].includes(versionPath)) { + activeVersion = versionPath; + } + }); return activeVersion; }, }, diff --git a/spec/frontend/default/components/helpers/versions_menu_helper.js b/spec/frontend/default/components/helpers/versions_menu_helper.js new file mode 100644 index 00000000..bdc1fa88 --- /dev/null +++ b/spec/frontend/default/components/helpers/versions_menu_helper.js @@ -0,0 +1,14 @@ +/** + * Creates a mock browser window object with a given path. + * @param {String} pathname + */ +export const setWindowPath = (pathname) => { + const location = { + ...window.location, + pathname, + }; + Object.defineProperty(window, 'location', { + writable: true, + value: location, + }); +}; diff --git a/spec/frontend/default/components/versions_menu_spec.js b/spec/frontend/default/components/versions_menu_spec.js index e7cadd20..01bb43e2 100644 --- a/spec/frontend/default/components/versions_menu_spec.js +++ b/spec/frontend/default/components/versions_menu_spec.js @@ -6,22 +6,82 @@ import { mount } from '@vue/test-utils'; import flushPromises from 'flush-promises'; import VersionsMenu from '../../../../content/frontend/default/components/versions_menu.vue'; import { getVersions } from '../../../../content/frontend/services/fetch_versions'; +import { setWindowPath } from './helpers/versions_menu_helper'; jest.mock('../../../../content/frontend/services/fetch_versions'); +const mockVersions = { + next: '15.3', + current: '15.2', + last_minor: ['15.1', '15.0'], + last_major: ['14.10', '13.12'], +}; + beforeEach(() => { jest.clearAllMocks(); + getVersions.mockResolvedValueOnce(mockVersions); }); describe('component: Versions menu', () => { it('Fetches versions.json and displays current version', async () => { - const mockNextVersion = '15.2'; - getVersions.mockResolvedValueOnce({ next: mockNextVersion }); const wrapper = mount(VersionsMenu); - await flushPromises(); + expect(getVersions).toHaveBeenCalledTimes(1); const nextVersion = wrapper.find('[data-testid="next-version"]').element.textContent; - expect(nextVersion).toEqual(mockNextVersion); + expect(nextVersion).toEqual(mockVersions.next); + }); + + it('Generates correct menu links from the homepage', async () => { + setWindowPath('/'); + const wrapper = mount(VersionsMenu); + + expect(wrapper.vm.getVersionPath('')).toBe('/'); + expect(wrapper.vm.getVersionPath(mockVersions.current)).toBe(`/${mockVersions.current}/`); + + Object.values([...mockVersions.last_major, ...mockVersions.last_minor]).forEach( + function testLink(v) { + expect(wrapper.vm.getVersionPath(v)).toBe(`/${v}/`); + }, + ); + }); + + it('Generates correct menu links from an interior page', async () => { + setWindowPath('/ee/user/project/issue_board.html'); + const wrapper = mount(VersionsMenu); + await wrapper.setData({ activeVersion: '15.3', versions: mockVersions }); + + expect(wrapper.vm.getVersionPath('')).toBe('/ee/user/project/issue_board.html'); + expect(wrapper.vm.getVersionPath(mockVersions.current)).toBe( + `/${mockVersions.current}/ee/user/project/issue_board.html`, + ); + + Object.values([...mockVersions.last_major, ...mockVersions.last_minor]).forEach( + function testLink(v) { + expect(wrapper.vm.getVersionPath(v)).toBe(`/${v}/ee/user/project/issue_board.html`); + }, + ); + }); + + it('Generates correct menu links from an older version', async () => { + setWindowPath('/14.10/runner'); + const wrapper = mount(VersionsMenu); + await wrapper.setData({ activeVersion: '14.10', versions: mockVersions }); + + expect(wrapper.vm.getVersionPath('')).toBe('/runner'); + expect(wrapper.vm.getVersionPath(mockVersions.current)).toBe(`/${mockVersions.current}/runner`); + + Object.values([...mockVersions.last_major, ...mockVersions.last_minor]).forEach( + function testLink(v) { + expect(wrapper.vm.getVersionPath(v)).toBe(`/${v}/runner`); + }, + ); + }); + + it('Detects the active version from the page URL', async () => { + setWindowPath('/14.10/runner'); + const wrapper = mount(VersionsMenu); + await flushPromises(); + expect(wrapper.vm.getActiveVersion(mockVersions)).toBe('14.10'); }); }); |