diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2020-02-13 15:08:52 +0000 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2020-02-13 15:08:52 +0000 |
commit | 0ab47b994caa80c5587f33dc818626b66cfdafe2 (patch) | |
tree | 5ef3976d2f84e3368903a67ba2dbd87a74b9a43c /spec/frontend | |
parent | 1308dc5eb484ab0f8064989fc551ebdb4b1a7976 (diff) | |
download | gitlab-ce-0ab47b994caa80c5587f33dc818626b66cfdafe2.tar.gz |
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'spec/frontend')
-rw-r--r-- | spec/frontend/diffs/components/diff_table_cell_spec.js (renamed from spec/frontend/diffs/components/diff_line_gutter_content_spec.js) | 44 | ||||
-rw-r--r-- | spec/frontend/monitoring/components/charts/time_series_spec.js | 75 | ||||
-rw-r--r-- | spec/frontend/snippet/collapsible_input_spec.js | 104 |
3 files changed, 186 insertions, 37 deletions
diff --git a/spec/frontend/diffs/components/diff_line_gutter_content_spec.js b/spec/frontend/diffs/components/diff_table_cell_spec.js index 0553498bfa0..1af0746f3bd 100644 --- a/spec/frontend/diffs/components/diff_line_gutter_content_spec.js +++ b/spec/frontend/diffs/components/diff_table_cell_spec.js @@ -1,6 +1,6 @@ +import { createLocalVue, shallowMount } from '@vue/test-utils'; import Vuex from 'vuex'; -import { shallowMount, createLocalVue } from '@vue/test-utils'; -import DiffLineGutterContent from '~/diffs/components/diff_line_gutter_content.vue'; +import DiffTableCell from '~/diffs/components/diff_table_cell.vue'; import DiffGutterAvatars from '~/diffs/components/diff_gutter_avatars.vue'; import { LINE_POSITION_RIGHT } from '~/diffs/constants'; import { createStore } from '~/mr_notes/stores'; @@ -17,7 +17,7 @@ const TEST_LINE_NUMBER = 1; const TEST_LINE_CODE = 'LC_42'; const TEST_FILE_HASH = diffFileMockData.file_hash; -describe('DiffLineGutterContent', () => { +describe('DiffTableCell', () => { let wrapper; let line; let store; @@ -49,22 +49,40 @@ describe('DiffLineGutterContent', () => { value, }); }; + const createComponent = (props = {}) => { - wrapper = shallowMount(DiffLineGutterContent, { + wrapper = shallowMount(DiffTableCell, { localVue, store, propsData: { line, fileHash: TEST_FILE_HASH, contextLinesPath: '/context/lines/path', + isHighlighted: false, ...props, }, }); }; - const findNoteButton = () => wrapper.find('.js-add-diff-note-button'); + + const findTd = () => wrapper.find({ ref: 'td' }); + const findNoteButton = () => wrapper.find({ ref: 'addDiffNoteButton' }); const findLineNumber = () => wrapper.find({ ref: 'lineNumberRef' }); const findAvatars = () => wrapper.find(DiffGutterAvatars); + describe('td', () => { + it('highlights when isHighlighted true', () => { + createComponent({ isHighlighted: true }); + + expect(findTd().classes()).toContain('hll'); + }); + + it('does not highlight when isHighlighted false', () => { + createComponent({ isHighlighted: false }); + + expect(findTd().classes()).not.toContain('hll'); + }); + }); + describe('comment button', () => { it.each` showCommentButton | userData | query | expectation @@ -84,13 +102,13 @@ describe('DiffLineGutterContent', () => { ); it.each` - isHover | otherProps | discussions | expectation - ${true} | ${{}} | ${[]} | ${true} - ${false} | ${{}} | ${[]} | ${false} - ${true} | ${{ isMatchLine: true }} | ${[]} | ${false} - ${true} | ${{ isContextLine: true }} | ${[]} | ${false} - ${true} | ${{ isMetaLine: true }} | ${[]} | ${false} - ${true} | ${{}} | ${[{}]} | ${false} + isHover | otherProps | discussions | expectation + ${true} | ${{}} | ${[]} | ${true} + ${false} | ${{}} | ${[]} | ${false} + ${true} | ${{ line: { ...line, type: 'match' } }} | ${[]} | ${false} + ${true} | ${{ line: { ...line, type: 'context' } }} | ${[]} | ${false} + ${true} | ${{ line: { ...line, type: 'old-nonewline' } }} | ${[]} | ${false} + ${true} | ${{}} | ${[{}]} | ${false} `( 'visible is $expectation - with isHover ($isHover), discussions ($discussions), otherProps ($otherProps)', ({ isHover, otherProps, discussions, expectation }) => { @@ -109,7 +127,7 @@ describe('DiffLineGutterContent', () => { describe('line number', () => { describe('without lineNumber prop', () => { it('does not render', () => { - createComponent(); + createComponent({ lineType: 'old' }); expect(findLineNumber().exists()).toBe(false); }); diff --git a/spec/frontend/monitoring/components/charts/time_series_spec.js b/spec/frontend/monitoring/components/charts/time_series_spec.js index 0a7e3dca183..4871619c85a 100644 --- a/spec/frontend/monitoring/components/charts/time_series_spec.js +++ b/spec/frontend/monitoring/components/charts/time_series_spec.js @@ -74,6 +74,8 @@ describe('Time series component', () => { describe('general functions', () => { let timeSeriesChart; + const findChart = () => timeSeriesChart.find({ ref: 'chart' }); + beforeEach(done => { timeSeriesChart = makeTimeSeriesChart(mockGraphData, 'area-chart'); timeSeriesChart.vm.$nextTick(done); @@ -109,8 +111,6 @@ describe('Time series component', () => { let startValue; let endValue; - const findChart = () => timeSeriesChart.find({ ref: 'chart' }); - beforeEach(done => { eChartMock = { handlers: {}, @@ -285,6 +285,8 @@ describe('Time series component', () => { }); describe('computed', () => { + const getChartOptions = () => findChart().props('option'); + describe('chartData', () => { let chartData; const seriesData = () => chartData[0]; @@ -329,7 +331,7 @@ describe('Time series component', () => { }); return timeSeriesChart.vm.$nextTick().then(() => { - expect(timeSeriesChart.vm.chartOptions).toEqual(expect.objectContaining(mockOption)); + expect(getChartOptions()).toEqual(expect.objectContaining(mockOption)); }); }); @@ -345,7 +347,7 @@ describe('Time series component', () => { }); return timeSeriesChart.vm.$nextTick().then(() => { - const optionSeries = timeSeriesChart.vm.chartOptions.series; + const optionSeries = getChartOptions().series; expect(optionSeries.length).toEqual(2); expect(optionSeries[0].name).toEqual(mockSeriesName); @@ -354,33 +356,58 @@ describe('Time series component', () => { }); describe('yAxis formatter', () => { - let format; + let dataFormatter; + let deploymentFormatter; beforeEach(() => { - format = timeSeriesChart.vm.chartOptions.yAxis.axisLabel.formatter; + dataFormatter = getChartOptions().yAxis[0].axisLabel.formatter; + deploymentFormatter = getChartOptions().yAxis[1].axisLabel.formatter; }); it('rounds to 3 decimal places', () => { - expect(format(0.88888)).toBe('0.889'); + expect(dataFormatter(0.88888)).toBe('0.889'); + }); + + it('deployment formatter is set as is required to display a tooltip', () => { + expect(deploymentFormatter).toEqual(expect.any(Function)); }); }); }); - describe('scatterSeries', () => { + describe('deploymentSeries', () => { it('utilizes deployment data', () => { - expect(timeSeriesChart.vm.scatterSeries.data).toEqual([ - ['2019-07-16T10:14:25.589Z', 0], - ['2019-07-16T11:14:25.589Z', 0], - ['2019-07-16T12:14:25.589Z', 0], + expect(timeSeriesChart.vm.deploymentSeries.yAxisIndex).toBe(1); // same as deployment y axis + expect(timeSeriesChart.vm.deploymentSeries.data).toEqual([ + ['2019-07-16T10:14:25.589Z', expect.any(Number)], + ['2019-07-16T11:14:25.589Z', expect.any(Number)], + ['2019-07-16T12:14:25.589Z', expect.any(Number)], ]); - expect(timeSeriesChart.vm.scatterSeries.symbolSize).toBe(14); + expect(timeSeriesChart.vm.deploymentSeries.symbolSize).toBe(14); }); }); describe('yAxisLabel', () => { + it('y axis is configured correctly', () => { + const { yAxis } = getChartOptions(); + + expect(yAxis).toHaveLength(2); + + const [dataAxis, deploymentAxis] = yAxis; + + expect(dataAxis.boundaryGap).toHaveLength(2); + expect(dataAxis.scale).toBe(true); + + expect(deploymentAxis.show).toBe(false); + expect(deploymentAxis.min).toEqual(expect.any(Number)); + expect(deploymentAxis.max).toEqual(expect.any(Number)); + expect(deploymentAxis.min).toBeLessThan(deploymentAxis.max); + }); + it('constructs a label for the chart y-axis', () => { - expect(timeSeriesChart.vm.yAxisLabel).toBe('Memory Used per Pod'); + const { yAxis } = getChartOptions(); + + expect(yAxis[0].name).toBe('Memory Used per Pod'); }); }); }); @@ -405,7 +432,7 @@ describe('Time series component', () => { glChartComponents.forEach(dynamicComponent => { describe(`GitLab UI: ${dynamicComponent.chartType}`, () => { let timeSeriesAreaChart; - const findChart = () => timeSeriesAreaChart.find(dynamicComponent.component); + const findChartComponent = () => timeSeriesAreaChart.find(dynamicComponent.component); beforeEach(done => { timeSeriesAreaChart = makeTimeSeriesChart(mockGraphData, dynamicComponent.chartType); @@ -417,12 +444,12 @@ describe('Time series component', () => { }); it('is a Vue instance', () => { - expect(findChart().exists()).toBe(true); - expect(findChart().isVueInstance()).toBe(true); + expect(findChartComponent().exists()).toBe(true); + expect(findChartComponent().isVueInstance()).toBe(true); }); it('receives data properties needed for proper chart render', () => { - const props = findChart().props(); + const props = findChartComponent().props(); expect(props.data).toBe(timeSeriesAreaChart.vm.chartData); expect(props.option).toBe(timeSeriesAreaChart.vm.chartOptions); @@ -435,9 +462,9 @@ describe('Time series component', () => { timeSeriesAreaChart.vm.tooltip.title = mockTitle; timeSeriesAreaChart.vm.$nextTick(() => { - expect(shallowWrapperContainsSlotText(findChart(), 'tooltipTitle', mockTitle)).toBe( - true, - ); + expect( + shallowWrapperContainsSlotText(findChartComponent(), 'tooltipTitle', mockTitle), + ).toBe(true); done(); }); }); @@ -452,9 +479,9 @@ describe('Time series component', () => { }); it('uses deployment title', () => { - expect(shallowWrapperContainsSlotText(findChart(), 'tooltipTitle', 'Deployed')).toBe( - true, - ); + expect( + shallowWrapperContainsSlotText(findChartComponent(), 'tooltipTitle', 'Deployed'), + ).toBe(true); }); it('renders clickable commit sha in tooltip content', done => { diff --git a/spec/frontend/snippet/collapsible_input_spec.js b/spec/frontend/snippet/collapsible_input_spec.js new file mode 100644 index 00000000000..acd15164c95 --- /dev/null +++ b/spec/frontend/snippet/collapsible_input_spec.js @@ -0,0 +1,104 @@ +import setupCollapsibleInputs from '~/snippet/collapsible_input'; +import { setHTMLFixture } from 'helpers/fixtures'; + +describe('~/snippet/collapsible_input', () => { + let formEl; + let descriptionEl; + let titleEl; + let fooEl; + + beforeEach(() => { + setHTMLFixture(` + <form> + <div class="js-collapsible-input js-title"> + <div class="js-collapsed d-none"> + <input type="text" /> + </div> + <div class="js-expanded"> + <textarea>Hello World!</textarea> + </div> + </div> + <div class="js-collapsible-input js-description"> + <div class="js-collapsed"> + <input type="text" /> + </div> + <div class="js-expanded d-none"> + <textarea></textarea> + </div> + </div> + <input type="text" class="js-foo" /> + </form> + `); + + formEl = document.querySelector('form'); + titleEl = formEl.querySelector('.js-title'); + descriptionEl = formEl.querySelector('.js-description'); + fooEl = formEl.querySelector('.js-foo'); + + setupCollapsibleInputs(); + }); + + const findInput = el => el.querySelector('textarea,input'); + const findCollapsed = el => el.querySelector('.js-collapsed'); + const findExpanded = el => el.querySelector('.js-expanded'); + const findCollapsedInput = el => findInput(findCollapsed(el)); + const findExpandedInput = el => findInput(findExpanded(el)); + const focusIn = target => target.dispatchEvent(new Event('focusin', { bubbles: true })); + const expectIsCollapsed = (el, isCollapsed) => { + expect(findCollapsed(el).classList.contains('d-none')).toEqual(!isCollapsed); + expect(findExpanded(el).classList.contains('d-none')).toEqual(isCollapsed); + }; + + describe('when collapsed', () => { + it('is collapsed', () => { + expectIsCollapsed(descriptionEl, true); + }); + + describe('when focused', () => { + beforeEach(() => { + focusIn(findCollapsedInput(descriptionEl)); + }); + + it('is expanded', () => { + expectIsCollapsed(descriptionEl, false); + }); + + describe.each` + desc | value | isCollapsed + ${'is collapsed'} | ${''} | ${true} + ${'stays open if given value'} | ${'Hello world!'} | ${false} + `('when loses focus', ({ desc, value, isCollapsed }) => { + it(desc, () => { + findExpandedInput(descriptionEl).value = value; + focusIn(fooEl); + + expectIsCollapsed(descriptionEl, isCollapsed); + }); + }); + }); + }); + + describe('when expanded and has value', () => { + it('does not collapse, when focusing out', () => { + expectIsCollapsed(titleEl, false); + + focusIn(fooEl); + + expectIsCollapsed(titleEl, false); + }); + + describe('and loses value', () => { + beforeEach(() => { + findExpandedInput(titleEl).value = ''; + }); + + it('collapses, when focusing out', () => { + expectIsCollapsed(titleEl, false); + + focusIn(fooEl); + + expectIsCollapsed(titleEl, true); + }); + }); + }); +}); |