Commit fac7694b authored by Kushal Pandya's avatar Kushal Pandya

Merge branch '284471-fix-vulnerability-report-double-requests' into 'master'

Fix duplicate request on vulnerability report page load

See merge request gitlab-org/gitlab!58523
parents ec4266b7 fa57ea52
...@@ -40,7 +40,7 @@ export default { ...@@ -40,7 +40,7 @@ export default {
}, },
data() { data() {
return { return {
filters: {}, filters: null,
projects: [], projects: [],
}; };
}, },
......
...@@ -18,7 +18,7 @@ export default { ...@@ -18,7 +18,7 @@ export default {
filters: { filters: {
type: Object, type: Object,
required: false, required: false,
default: () => ({}), default: null,
}, },
}, },
data() { data() {
...@@ -48,6 +48,9 @@ export default { ...@@ -48,6 +48,9 @@ export default {
error() { error() {
this.errorLoadingVulnerabilities = true; this.errorLoadingVulnerabilities = true;
}, },
skip() {
return !this.filters;
},
}, },
}, },
computed: { computed: {
......
...@@ -36,7 +36,7 @@ export default { ...@@ -36,7 +36,7 @@ export default {
}, },
data() { data() {
return { return {
filters: {}, filters: null,
projects: [], projects: [],
}; };
}, },
......
...@@ -18,7 +18,7 @@ export default { ...@@ -18,7 +18,7 @@ export default {
filters: { filters: {
type: Object, type: Object,
required: false, required: false,
default: () => ({}), default: null,
}, },
}, },
data() { data() {
...@@ -59,6 +59,9 @@ export default { ...@@ -59,6 +59,9 @@ export default {
error() { error() {
this.errorLoadingVulnerabilities = true; this.errorLoadingVulnerabilities = true;
}, },
skip() {
return !this.filters;
},
}, },
}, },
watch: { watch: {
......
...@@ -41,7 +41,7 @@ export default { ...@@ -41,7 +41,7 @@ export default {
const shouldShowAutoFixUserCallout = const shouldShowAutoFixUserCallout =
this.glFeatures.securityAutoFix && !Cookies.get('auto_fix_user_callout_dismissed'); this.glFeatures.securityAutoFix && !Cookies.get('auto_fix_user_callout_dismissed');
return { return {
filters: {}, filters: null,
shouldShowAutoFixUserCallout, shouldShowAutoFixUserCallout,
}; };
}, },
......
...@@ -28,7 +28,7 @@ export default { ...@@ -28,7 +28,7 @@ export default {
filters: { filters: {
type: Object, type: Object,
required: false, required: false,
default: () => ({}), default: null,
}, },
}, },
data() { data() {
...@@ -60,6 +60,9 @@ export default { ...@@ -60,6 +60,9 @@ export default {
error() { error() {
this.errorLoadingVulnerabilities = true; this.errorLoadingVulnerabilities = true;
}, },
skip() {
return !this.filters;
},
}, },
securityScanners: { securityScanners: {
query: securityScannersQuery, query: securityScannersQuery,
......
...@@ -22,7 +22,7 @@ export default { ...@@ -22,7 +22,7 @@ export default {
filters: { filters: {
type: Object, type: Object,
required: false, required: false,
default: () => ({}), default: null,
}, },
}, },
data() { data() {
...@@ -64,6 +64,9 @@ export default { ...@@ -64,6 +64,9 @@ export default {
error() { error() {
this.queryError = true; this.queryError = true;
}, },
skip() {
return !this.filters;
},
}, },
}, },
}; };
......
...@@ -71,7 +71,11 @@ describe('First Class Group Dashboard Component', () => { ...@@ -71,7 +71,11 @@ describe('First Class Group Dashboard Component', () => {
describe('when has projects', () => { describe('when has projects', () => {
beforeEach(() => { beforeEach(() => {
wrapper = createWrapper({ wrapper = createWrapper({
data: () => ({ projects: [{ id: 1, name: 'GitLab Org' }], projectsWereFetched: true }), data: () => ({
projects: [{ id: 1, name: 'GitLab Org' }],
projectsWereFetched: true,
filters: {},
}),
}); });
}); });
......
import { GlAlert, GlTable, GlEmptyState, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui'; import { GlAlert, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils'; import { shallowMount, createLocalVue } from '@vue/test-utils';
import VueApollo from 'vue-apollo';
import FirstClassGroupVulnerabilities from 'ee/security_dashboard/components/first_class_group_security_dashboard_vulnerabilities.vue'; import FirstClassGroupVulnerabilities from 'ee/security_dashboard/components/first_class_group_security_dashboard_vulnerabilities.vue';
import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue'; import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue';
import vulnerabilitiesQuery from 'ee/security_dashboard/graphql/queries/group_vulnerabilities.query.graphql';
import createMockApollo from 'helpers/mock_apollo_helper';
import { generateVulnerabilities } from './mock_data'; import { generateVulnerabilities } from './mock_data';
const localVue = createLocalVue();
localVue.use(VueApollo);
describe('First Class Group Dashboard Vulnerabilities Component', () => { describe('First Class Group Dashboard Vulnerabilities Component', () => {
let wrapper; let wrapper;
const apolloMock = { const apolloMock = {
...@@ -22,13 +28,15 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => { ...@@ -22,13 +28,15 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => {
expect(findLoadingIcon().exists()).toBe(nextPage); expect(findLoadingIcon().exists()).toBe(nextPage);
}; };
const createWrapper = ({ $apollo = apolloMock, stubs } = {}) => { const createWrapper = ({ $apollo = apolloMock } = {}) => {
return shallowMount(FirstClassGroupVulnerabilities, { return shallowMount(FirstClassGroupVulnerabilities, {
stubs,
mocks: { mocks: {
$apollo, $apollo,
fetchNextPage: () => {}, fetchNextPage: () => {},
}, },
propsData: {
filters: {},
},
provide: { provide: {
groupFullPath, groupFullPath,
hasVulnerabilities: true, hasVulnerabilities: true,
...@@ -61,9 +69,6 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => { ...@@ -61,9 +69,6 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => {
$apollo: { $apollo: {
queries: { vulnerabilities: { loading: false } }, queries: { vulnerabilities: { loading: false } },
}, },
stubs: {
GlAlert,
},
}); });
wrapper.setData({ wrapper.setData({
...@@ -98,11 +103,6 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => { ...@@ -98,11 +103,6 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => {
$apollo: { $apollo: {
queries: { vulnerabilities: { loading: false } }, queries: { vulnerabilities: { loading: false } },
}, },
stubs: {
VulnerabilityList,
GlTable,
GlEmptyState,
},
}); });
wrapper.setData({ wrapper.setData({
...@@ -207,4 +207,38 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => { ...@@ -207,4 +207,38 @@ describe('First Class Group Dashboard Vulnerabilities Component', () => {
expectLoadingState({ initial: true }); expectLoadingState({ initial: true });
}); });
}); });
describe('filters prop', () => {
const mockQuery = jest.fn().mockResolvedValue({
data: {
group: {
vulnerabilities: {
nodes: [],
pageInfo: { startCursor: '', endCursor: '' },
},
},
},
});
const createWrapperWithApollo = ({ query, filters }) => {
wrapper = shallowMount(FirstClassGroupVulnerabilities, {
localVue,
apolloProvider: createMockApollo([[vulnerabilitiesQuery, query]]),
propsData: { filters },
provide: { groupFullPath: 'path' },
});
};
it('does not run the query when filters is null', () => {
createWrapperWithApollo({ query: mockQuery, filters: null });
expect(mockQuery).not.toHaveBeenCalled();
});
it('runs query when filters is an object', () => {
createWrapperWithApollo({ query: mockQuery, filters: {} });
expect(mockQuery).toHaveBeenCalled();
});
});
}); });
...@@ -57,9 +57,7 @@ describe('First Class Instance Dashboard Component', () => { ...@@ -57,9 +57,7 @@ describe('First Class Instance Dashboard Component', () => {
}); });
it('should render the vulnerabilities', () => { it('should render the vulnerabilities', () => {
expect(findInstanceVulnerabilities().props()).toEqual({ expect(findInstanceVulnerabilities().exists()).toBe(true);
filters: {},
});
}); });
it('should show the survey banner', () => { it('should show the survey banner', () => {
......
import { GlAlert, GlTable, GlEmptyState, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui'; import { GlAlert, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils'; import { createLocalVue, shallowMount } from '@vue/test-utils';
import VueApollo from 'vue-apollo';
import FirstClassInstanceVulnerabilities from 'ee/security_dashboard/components/first_class_instance_security_dashboard_vulnerabilities.vue'; import FirstClassInstanceVulnerabilities from 'ee/security_dashboard/components/first_class_instance_security_dashboard_vulnerabilities.vue';
import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue'; import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue';
import vulnerabilitiesQuery from 'ee/security_dashboard/graphql/queries/instance_vulnerabilities.query.graphql';
import createMockApollo from 'helpers/mock_apollo_helper';
import { generateVulnerabilities } from './mock_data'; import { generateVulnerabilities } from './mock_data';
const localVue = createLocalVue();
localVue.use(VueApollo);
describe('First Class Instance Dashboard Vulnerabilities Component', () => { describe('First Class Instance Dashboard Vulnerabilities Component', () => {
let wrapper; let wrapper;
...@@ -17,9 +23,8 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -17,9 +23,8 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
expect(findLoadingIcon().exists()).toBe(nextPage); expect(findLoadingIcon().exists()).toBe(nextPage);
}; };
const createWrapper = ({ stubs, loading = false, data } = {}) => { const createWrapper = ({ loading = false, data } = {}) => {
return shallowMount(FirstClassInstanceVulnerabilities, { return shallowMount(FirstClassInstanceVulnerabilities, {
stubs,
mocks: { mocks: {
$apollo: { $apollo: {
queries: { vulnerabilities: { loading } }, queries: { vulnerabilities: { loading } },
...@@ -27,6 +32,9 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -27,6 +32,9 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
fetchNextPage: () => {}, fetchNextPage: () => {},
}, },
data, data,
propsData: {
filters: {},
},
provide: { provide: {
hasVulnerabilities: true, hasVulnerabilities: true,
hasJiraVulnerabilitiesIntegrationEnabled: false, hasJiraVulnerabilitiesIntegrationEnabled: false,
...@@ -36,7 +44,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -36,7 +44,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
afterEach(() => { afterEach(() => {
wrapper.destroy(); wrapper.destroy();
wrapper = null;
}); });
describe('when the query is loading', () => { describe('when the query is loading', () => {
...@@ -52,9 +59,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -52,9 +59,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
describe('when the query returned an error status', () => { describe('when the query returned an error status', () => {
beforeEach(() => { beforeEach(() => {
wrapper = createWrapper({ wrapper = createWrapper({
stubs: {
GlAlert,
},
data: () => ({ errorLoadingVulnerabilities: true }), data: () => ({ errorLoadingVulnerabilities: true }),
}); });
}); });
...@@ -83,11 +87,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -83,11 +87,6 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
beforeEach(() => { beforeEach(() => {
wrapper = createWrapper({ wrapper = createWrapper({
stubs: {
VulnerabilityList,
GlTable,
GlEmptyState,
},
data: () => ({ vulnerabilities }), data: () => ({ vulnerabilities }),
}); });
}); });
...@@ -194,4 +193,35 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => { ...@@ -194,4 +193,35 @@ describe('First Class Instance Dashboard Vulnerabilities Component', () => {
expectLoadingState({ initial: true }); expectLoadingState({ initial: true });
}); });
}); });
describe('filters prop', () => {
const mockQuery = jest.fn().mockResolvedValue({
data: {
vulnerabilities: {
nodes: [],
pageInfo: { startCursor: '', endCursor: '' },
},
},
});
const createWrapperWithApollo = ({ query, filters }) => {
wrapper = shallowMount(FirstClassInstanceVulnerabilities, {
localVue,
apolloProvider: createMockApollo([[vulnerabilitiesQuery, query]]),
propsData: { filters },
});
};
it('does not run the query when filters is null', () => {
createWrapperWithApollo({ query: mockQuery, filters: null });
expect(mockQuery).not.toHaveBeenCalled();
});
it('runs query when filters is an object', () => {
createWrapperWithApollo({ query: mockQuery, filters: {} });
expect(mockQuery).toHaveBeenCalled();
});
});
}); });
import { GlAlert, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui'; import { GlAlert, GlIntersectionObserver, GlLoadingIcon } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils'; import { shallowMount, createLocalVue } from '@vue/test-utils';
import VueApollo from 'vue-apollo';
import ProjectVulnerabilitiesApp from 'ee/security_dashboard/components/project_vulnerabilities.vue'; import ProjectVulnerabilitiesApp from 'ee/security_dashboard/components/project_vulnerabilities.vue';
import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue'; import VulnerabilityList from 'ee/security_dashboard/components/vulnerability_list.vue';
import vulnerabilitiesQuery from 'ee/security_dashboard/graphql/queries/project_vulnerabilities.query.graphql';
import createMockApollo from 'helpers/mock_apollo_helper';
import { generateVulnerabilities } from './mock_data'; import { generateVulnerabilities } from './mock_data';
const localVue = createLocalVue();
localVue.use(VueApollo);
describe('Vulnerabilities app component', () => { describe('Vulnerabilities app component', () => {
let wrapper; let wrapper;
const apolloMock = { const apolloMock = {
...@@ -180,4 +186,38 @@ describe('Vulnerabilities app component', () => { ...@@ -180,4 +186,38 @@ describe('Vulnerabilities app component', () => {
expect(findVulnerabilityList().props().securityScanners).toEqual(securityScanners); expect(findVulnerabilityList().props().securityScanners).toEqual(securityScanners);
}); });
}); });
describe('filters prop', () => {
const mockQuery = jest.fn().mockResolvedValue({
data: {
project: {
vulnerabilities: {
nodes: [],
pageInfo: { startCursor: '', endCursor: '' },
},
},
},
});
const createWrapperWithApollo = ({ query, filters }) => {
wrapper = shallowMount(ProjectVulnerabilitiesApp, {
localVue,
apolloProvider: createMockApollo([[vulnerabilitiesQuery, query]]),
propsData: { filters },
provide: { groupFullPath: 'path' },
});
};
it('does not run the query when filters is null', () => {
createWrapperWithApollo({ query: mockQuery, filters: null });
expect(mockQuery).not.toHaveBeenCalled();
});
it('runs query when filters is an object', () => {
createWrapperWithApollo({ query: mockQuery, filters: {} });
expect(mockQuery).toHaveBeenCalled();
});
});
}); });
import { shallowMount } from '@vue/test-utils'; import { shallowMount, createLocalVue } from '@vue/test-utils';
import VueApollo from 'vue-apollo';
import VulnerabilityCountList from 'ee/security_dashboard/components/vulnerability_count_list.vue'; import VulnerabilityCountList from 'ee/security_dashboard/components/vulnerability_count_list.vue';
import VulnerabilityCountListLayout from 'ee/security_dashboard/components/vulnerability_count_list_layout.vue'; import VulnerabilityCountListLayout from 'ee/security_dashboard/components/vulnerability_count_list_layout.vue';
import countQuery from 'ee/security_dashboard/graphql/queries/vulnerability_severities_count.query.graphql';
import eventHub from 'ee/security_dashboard/utils/event_hub'; import eventHub from 'ee/security_dashboard/utils/event_hub';
import createMockApollo from 'helpers/mock_apollo_helper';
const localVue = createLocalVue();
localVue.use(VueApollo);
describe('Vulnerabilities count list component', () => { describe('Vulnerabilities count list component', () => {
let wrapper; let wrapper;
...@@ -98,4 +104,28 @@ describe('Vulnerabilities count list component', () => { ...@@ -98,4 +104,28 @@ describe('Vulnerabilities count list component', () => {
expect(findVulnerabilityLayout().props('showError')).toBe(true); expect(findVulnerabilityLayout().props('showError')).toBe(true);
}); });
}); });
describe('filters prop', () => {
const mockQuery = jest.fn().mockResolvedValue(null);
const createWrapperWithApollo = ({ query, filters }) => {
wrapper = shallowMount(VulnerabilityCountList, {
localVue,
apolloProvider: createMockApollo([[countQuery, query]]),
propsData: { scope: 'project', filters },
});
};
it('does not run the query when filters is null', () => {
createWrapperWithApollo({ query: mockQuery, filters: null });
expect(mockQuery).not.toHaveBeenCalled();
});
it('runs query when filters is an object', () => {
createWrapperWithApollo({ query: mockQuery, filters: {} });
expect(mockQuery).toHaveBeenCalled();
});
});
}); });
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