315 lines
9 KiB
JavaScript
315 lines
9 KiB
JavaScript
import { GlSearchBoxByClick } from '@gitlab/ui';
|
|
import { mount } from '@vue/test-utils';
|
|
import JobLogControllers from '~/jobs/components/job_log_controllers.vue';
|
|
import HelpPopover from '~/vue_shared/components/help_popover.vue';
|
|
import { backoffMockImplementation } from 'helpers/backoff_helper';
|
|
import * as commonUtils from '~/lib/utils/common_utils';
|
|
import { mockJobLog } from '../mock_data';
|
|
|
|
const mockToastShow = jest.fn();
|
|
|
|
describe('Job log controllers', () => {
|
|
let wrapper;
|
|
|
|
beforeEach(() => {
|
|
jest.spyOn(commonUtils, 'backOff').mockImplementation(backoffMockImplementation);
|
|
});
|
|
|
|
afterEach(() => {
|
|
if (wrapper?.destroy) {
|
|
wrapper.destroy();
|
|
}
|
|
commonUtils.backOff.mockReset();
|
|
});
|
|
|
|
const defaultProps = {
|
|
rawPath: '/raw',
|
|
erasePath: '/erase',
|
|
size: 511952,
|
|
isScrollTopDisabled: false,
|
|
isScrollBottomDisabled: false,
|
|
isScrollingDown: true,
|
|
isJobLogSizeVisible: true,
|
|
isComplete: true,
|
|
jobLog: mockJobLog,
|
|
};
|
|
|
|
const createWrapper = (props, { jobLogJumpToFailures = false } = {}) => {
|
|
wrapper = mount(JobLogControllers, {
|
|
propsData: {
|
|
...defaultProps,
|
|
...props,
|
|
},
|
|
provide: {
|
|
glFeatures: {
|
|
jobLogJumpToFailures,
|
|
},
|
|
},
|
|
data() {
|
|
return {
|
|
searchTerm: '82',
|
|
};
|
|
},
|
|
mocks: {
|
|
$toast: {
|
|
show: mockToastShow,
|
|
},
|
|
},
|
|
});
|
|
};
|
|
|
|
const findTruncatedInfo = () => wrapper.find('[data-testid="log-truncated-info"]');
|
|
const findRawLink = () => wrapper.find('[data-testid="raw-link"]');
|
|
const findRawLinkController = () => wrapper.find('[data-testid="job-raw-link-controller"]');
|
|
const findScrollTop = () => wrapper.find('[data-testid="job-controller-scroll-top"]');
|
|
const findScrollBottom = () => wrapper.find('[data-testid="job-controller-scroll-bottom"]');
|
|
const findJobLogSearch = () => wrapper.findComponent(GlSearchBoxByClick);
|
|
const findSearchHelp = () => wrapper.findComponent(HelpPopover);
|
|
const findScrollFailure = () => wrapper.find('[data-testid="job-controller-scroll-to-failure"]');
|
|
|
|
describe('Truncate information', () => {
|
|
describe('with isJobLogSizeVisible', () => {
|
|
beforeEach(() => {
|
|
createWrapper();
|
|
});
|
|
|
|
it('renders size information', () => {
|
|
expect(findTruncatedInfo().text()).toMatch('499.95 KiB');
|
|
});
|
|
|
|
it('renders link to raw job log', () => {
|
|
expect(findRawLink().attributes('href')).toBe(defaultProps.rawPath);
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('links section', () => {
|
|
describe('with raw job log path', () => {
|
|
beforeEach(() => {
|
|
createWrapper();
|
|
});
|
|
|
|
it('renders raw job log link', () => {
|
|
expect(findRawLinkController().attributes('href')).toBe(defaultProps.rawPath);
|
|
});
|
|
});
|
|
|
|
describe('without raw job log path', () => {
|
|
beforeEach(() => {
|
|
createWrapper({
|
|
rawPath: null,
|
|
});
|
|
});
|
|
|
|
it('does not render raw job log link', () => {
|
|
expect(findRawLinkController().exists()).toBe(false);
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('scroll buttons', () => {
|
|
describe('scroll top button', () => {
|
|
describe('when user can scroll top', () => {
|
|
beforeEach(() => {
|
|
createWrapper({
|
|
isScrollTopDisabled: false,
|
|
});
|
|
});
|
|
|
|
it('emits scrollJobLogTop event on click', async () => {
|
|
await findScrollTop().trigger('click');
|
|
|
|
expect(wrapper.emitted().scrollJobLogTop).toHaveLength(1);
|
|
});
|
|
});
|
|
|
|
describe('when user can not scroll top', () => {
|
|
beforeEach(() => {
|
|
createWrapper({
|
|
isScrollTopDisabled: true,
|
|
isScrollBottomDisabled: false,
|
|
isScrollingDown: false,
|
|
});
|
|
});
|
|
|
|
it('renders disabled scroll top button', () => {
|
|
expect(findScrollTop().attributes('disabled')).toBe('disabled');
|
|
});
|
|
|
|
it('does not emit scrollJobLogTop event on click', async () => {
|
|
await findScrollTop().trigger('click');
|
|
|
|
expect(wrapper.emitted().scrollJobLogTop).toBeUndefined();
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('scroll bottom button', () => {
|
|
describe('when user can scroll bottom', () => {
|
|
beforeEach(() => {
|
|
createWrapper();
|
|
});
|
|
|
|
it('emits scrollJobLogBottom event on click', async () => {
|
|
await findScrollBottom().trigger('click');
|
|
|
|
expect(wrapper.emitted().scrollJobLogBottom).toHaveLength(1);
|
|
});
|
|
});
|
|
|
|
describe('when user can not scroll bottom', () => {
|
|
beforeEach(() => {
|
|
createWrapper({
|
|
isScrollTopDisabled: false,
|
|
isScrollBottomDisabled: true,
|
|
isScrollingDown: false,
|
|
});
|
|
});
|
|
|
|
it('renders disabled scroll bottom button', () => {
|
|
expect(findScrollBottom().attributes('disabled')).toEqual('disabled');
|
|
});
|
|
|
|
it('does not emit scrollJobLogBottom event on click', async () => {
|
|
await findScrollBottom().trigger('click');
|
|
|
|
expect(wrapper.emitted().scrollJobLogBottom).toBeUndefined();
|
|
});
|
|
});
|
|
|
|
describe('while isScrollingDown is true', () => {
|
|
beforeEach(() => {
|
|
createWrapper();
|
|
});
|
|
|
|
it('renders animate class for the scroll down button', () => {
|
|
expect(findScrollBottom().classes()).toContain('animate');
|
|
});
|
|
});
|
|
|
|
describe('while isScrollingDown is false', () => {
|
|
beforeEach(() => {
|
|
createWrapper({
|
|
isScrollTopDisabled: true,
|
|
isScrollBottomDisabled: false,
|
|
isScrollingDown: false,
|
|
});
|
|
});
|
|
|
|
it('does not render animate class for the scroll down button', () => {
|
|
expect(findScrollBottom().classes()).not.toContain('animate');
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('scroll to failure button', () => {
|
|
describe('with feature flag disabled', () => {
|
|
it('does not display button', () => {
|
|
createWrapper();
|
|
|
|
expect(findScrollFailure().exists()).toBe(false);
|
|
});
|
|
});
|
|
|
|
describe('with red text failures on the page', () => {
|
|
let firstFailure;
|
|
let secondFailure;
|
|
|
|
beforeEach(() => {
|
|
jest.spyOn(document, 'querySelectorAll').mockReturnValueOnce(['mock-element']);
|
|
|
|
createWrapper({}, { jobLogJumpToFailures: true });
|
|
|
|
firstFailure = document.createElement('div');
|
|
firstFailure.className = 'term-fg-l-red';
|
|
document.body.appendChild(firstFailure);
|
|
|
|
secondFailure = document.createElement('div');
|
|
secondFailure.className = 'term-fg-l-red';
|
|
document.body.appendChild(secondFailure);
|
|
});
|
|
|
|
afterEach(() => {
|
|
if (firstFailure) {
|
|
firstFailure.remove();
|
|
firstFailure = null;
|
|
}
|
|
|
|
if (secondFailure) {
|
|
secondFailure.remove();
|
|
secondFailure = null;
|
|
}
|
|
});
|
|
|
|
it('is enabled', () => {
|
|
expect(findScrollFailure().props('disabled')).toBe(false);
|
|
});
|
|
|
|
it('scrolls to each failure', async () => {
|
|
jest.spyOn(firstFailure, 'scrollIntoView');
|
|
|
|
await findScrollFailure().trigger('click');
|
|
|
|
expect(firstFailure.scrollIntoView).toHaveBeenCalled();
|
|
|
|
await findScrollFailure().trigger('click');
|
|
|
|
expect(secondFailure.scrollIntoView).toHaveBeenCalled();
|
|
|
|
await findScrollFailure().trigger('click');
|
|
|
|
expect(firstFailure.scrollIntoView).toHaveBeenCalled();
|
|
});
|
|
});
|
|
|
|
describe('with no red text failures on the page', () => {
|
|
beforeEach(() => {
|
|
jest.spyOn(document, 'querySelectorAll').mockReturnValueOnce([]);
|
|
|
|
createWrapper({}, { jobLogJumpToFailures: true });
|
|
});
|
|
|
|
it('is disabled', () => {
|
|
expect(findScrollFailure().props('disabled')).toBe(true);
|
|
});
|
|
});
|
|
|
|
describe('when the job log is not complete', () => {
|
|
beforeEach(() => {
|
|
jest.spyOn(document, 'querySelectorAll').mockReturnValueOnce(['mock-element']);
|
|
|
|
createWrapper({ isComplete: false }, { jobLogJumpToFailures: true });
|
|
});
|
|
|
|
it('is enabled', () => {
|
|
expect(findScrollFailure().props('disabled')).toBe(false);
|
|
});
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('Job log search', () => {
|
|
beforeEach(() => {
|
|
createWrapper();
|
|
});
|
|
|
|
it('displays job log search', () => {
|
|
expect(findJobLogSearch().exists()).toBe(true);
|
|
expect(findSearchHelp().exists()).toBe(true);
|
|
});
|
|
|
|
it('emits search results', () => {
|
|
const expectedSearchResults = [[[mockJobLog[6].lines[1], mockJobLog[6].lines[2]]]];
|
|
|
|
findJobLogSearch().vm.$emit('submit');
|
|
|
|
expect(wrapper.emitted('searchResults')).toEqual(expectedSearchResults);
|
|
});
|
|
|
|
it('clears search results', () => {
|
|
findJobLogSearch().vm.$emit('clear');
|
|
|
|
expect(wrapper.emitted('searchResults')).toEqual([[[]]]);
|
|
});
|
|
});
|
|
});
|