Commit d87f2e8f authored by Bob Van Landuyt's avatar Bob Van Landuyt

Merge branch 'secure-delete-pipelines' into 'master'

Delete old pipelines security report

See merge request gitlab-org/gitlab!22152
parents c10e3d61 5d662ff4
......@@ -2,8 +2,6 @@ import Vue from 'vue';
import { GlEmptyState } from '@gitlab/ui';
import createDashboardStore from 'ee/security_dashboard/store';
import SecurityDashboardApp from 'ee/security_dashboard/components/app.vue';
import SecurityReportApp from 'ee/vue_shared/security_reports/split_security_reports_app.vue';
import createStore from 'ee/vue_shared/security_reports/store';
import { s__ } from '~/locale';
import Translate from '~/vue_shared/translate';
......@@ -53,71 +51,10 @@ const initSecurityDashboardApp = el => {
});
};
const initSplitSecurityReportsApp = el => {
const datasetOptions = el.dataset;
const {
headBlobPath,
sourceBranch,
sastHeadPath,
sastHelpPath,
dependencyScanningHeadPath,
dependencyScanningHelpPath,
vulnerabilityFeedbackPath,
vulnerabilityFeedbackHelpPath,
createVulnerabilityFeedbackIssuePath,
createVulnerabilityFeedbackMergeRequestPath,
createVulnerabilityFeedbackDismissalPath,
dastHeadPath,
sastContainerHeadPath,
dastHelpPath,
sastContainerHelpPath,
} = datasetOptions;
const pipelineId = parseInt(datasetOptions.pipelineId, 10);
const store = createStore();
return new Vue({
el,
store,
components: {
SecurityReportApp,
},
render(createElement) {
return createElement('security-report-app', {
props: {
headBlobPath,
sourceBranch,
sastHeadPath,
sastHelpPath,
dependencyScanningHeadPath,
dependencyScanningHelpPath,
vulnerabilityFeedbackPath,
vulnerabilityFeedbackHelpPath,
createVulnerabilityFeedbackIssuePath,
createVulnerabilityFeedbackMergeRequestPath,
createVulnerabilityFeedbackDismissalPath,
pipelineId,
dastHeadPath,
sastContainerHeadPath,
dastHelpPath,
sastContainerHelpPath,
canCreateIssue: Boolean(createVulnerabilityFeedbackIssuePath),
canCreateMergeRequest: Boolean(createVulnerabilityFeedbackMergeRequestPath),
canDismissVulnerability: Boolean(createVulnerabilityFeedbackDismissalPath),
},
});
},
});
};
export default () => {
const securityTab = document.getElementById('js-security-report-app');
if (securityTab) {
if (gon.features && gon.features.pipelineReportApi) {
initSecurityDashboardApp(securityTab);
} else {
initSplitSecurityReportsApp(securityTab);
}
initSecurityDashboardApp(securityTab);
}
};
......@@ -12,7 +12,6 @@ module EE
# because the user can freely navigate between them *without*
# triggering a page load.
before_action only: [:show, :builds, :failures, :security, :licenses] do
push_frontend_feature_flag(:pipeline_report_api, default_enabled: true)
push_frontend_feature_flag(:parsed_license_report, default_enabled: true)
end
end
......
- pipeline = local_assigns.fetch(:pipeline)
- project = local_assigns.fetch(:project)
- sast_endpoint = pipeline.downloadable_path_for_report_type(:sast)
- dependency_scanning_endpoint = pipeline.downloadable_path_for_report_type(:dependency_scanning)
- dast_endpoint = pipeline.downloadable_path_for_report_type(:dast)
- sast_container_endpoint = pipeline.downloadable_path_for_report_type(:container_scanning)
- blob_path = project_blob_path(project, pipeline.sha)
- license_management_settings_path = can?(current_user, :admin_software_license_policy, project) ? license_management_settings_path(project) : nil
- licenses_api_path = licenses_project_pipeline_path(project, pipeline) if project.feature_available?(:license_management)
- vulnerabilities_endpoint_path = expose_path(api_v4_projects_vulnerability_findings_path(id: project.id, params: { pipeline_id: pipeline.id, scope: 'dismissed' }))
- if pipeline.expose_security_dashboard?
#js-tab-security.build-security.tab-pane
- if Feature.enabled?(:pipeline_report_api, default_enabled: true)
#js-security-report-app{ data: { dashboard_documentation: help_page_path('user/application_security/security_dashboard/index'),
empty_state_svg_path: image_path('illustrations/security-dashboard-empty-state.svg'),
pipeline_id: pipeline.id,
project_id: project.id,
vulnerabilities_endpoint: vulnerabilities_endpoint_path,
vulnerability_feedback_help_path: help_page_path('user/application_security/index') } }
- else
#js-security-report-app{ data: { head_blob_path: blob_path,
sast_head_path: sast_endpoint,
dependency_scanning_head_path: dependency_scanning_endpoint,
dast_head_path: dast_endpoint,
sast_container_head_path: sast_container_endpoint,
pipeline_id: pipeline.id,
source_branch: pipeline.ref,
vulnerability_feedback_path: project_vulnerability_feedback_index_path(project),
vulnerability_feedback_help_path: help_page_path('user/application_security/index'),
sast_help_path: help_page_path('user/application_security/sast/index'),
dependency_scanning_help_path: help_page_path('user/application_security/dependency_scanning/index'),
dast_help_path: help_page_path('user/application_security/dast/index'),
sast_container_help_path: help_page_path('user/application_security/container_scanning/index'),
create_vulnerability_feedback_issue_path: create_vulnerability_feedback_issue_path(project),
create_vulnerability_feedback_merge_request_path: create_vulnerability_feedback_merge_request_path(project),
create_vulnerability_feedback_dismissal_path: create_vulnerability_feedback_dismissal_path(project) } }
#js-security-report-app{ data: { dashboard_documentation: help_page_path('user/application_security/security_dashboard/index'),
empty_state_svg_path: image_path('illustrations/security-dashboard-empty-state.svg'),
pipeline_id: pipeline.id,
project_id: project.id,
vulnerabilities_endpoint: vulnerabilities_endpoint_path,
vulnerability_feedback_help_path: help_page_path('user/application_security/index') } }
- if pipeline.expose_license_scanning_data?
#js-tab-licenses.tab-pane
......
---
title: Remove old pipeline security report view in favor of the Security Dashboard
merge_request: 22152
author:
type: removed
......@@ -101,37 +101,16 @@ describe 'Pipeline', :js do
context 'with a sast artifact' do
before do
create(:ee_ci_build, :sast, pipeline: pipeline)
visit security_project_pipeline_path(project, pipeline)
end
context 'when feature flag is enabled' do
before do
visit security_project_pipeline_path(project, pipeline)
end
it 'shows jobs tab pane as active' do
expect(page).to have_content('Security')
expect(page).to have_css('#js-tab-security')
end
it 'shows security dashboard' do
expect(page).to have_css('.js-security-dashboard-table')
end
it 'shows jobs tab pane as active' do
expect(page).to have_content('Security')
expect(page).to have_css('#js-tab-security')
end
context 'when feature flag is disabled' do
before do
stub_feature_flags(pipeline_report_api: false)
visit security_project_pipeline_path(project, pipeline)
end
it 'shows jobs tab pane as active' do
expect(page).to have_content('Security')
expect(page).to have_css('#js-tab-security')
end
it 'shows security report section' do
expect(page).to have_content('SAST is loading')
end
it 'shows security dashboard' do
expect(page).to have_css('.js-security-dashboard-table')
end
end
......
import Vue from 'vue';
import MockAdapter from 'axios-mock-adapter';
import component from 'ee/vue_shared/security_reports/split_security_reports_app.vue';
import createStore from 'ee/vue_shared/security_reports/store';
import state from 'ee/vue_shared/security_reports/store/state';
import { mountComponentWithStore } from 'spec/helpers/vue_mount_component_helper';
import axios from '~/lib/utils/axios_utils';
import { sastIssues, dast, dockerReport } from './mock_data';
describe('Split security reports app', () => {
const Component = Vue.extend(component);
let vm;
let mock;
beforeEach(() => {
mock = new MockAdapter(axios);
});
afterEach(() => {
vm.$store.replaceState(state());
vm.$destroy();
mock.restore();
});
describe('while loading', () => {
beforeEach(() => {
mock.onGet('sast_head.json').reply(200, sastIssues);
mock.onGet('dss_head.json').reply(200, sastIssues);
mock.onGet('dast_head.json').reply(200, dast);
mock.onGet('sast_container_head.json').reply(200, dockerReport);
mock.onGet('vulnerability_feedback_path.json').reply(200, []);
vm = mountComponentWithStore(Component, {
store: createStore(),
props: {
headBlobPath: 'path',
sastHeadPath: 'sast_head.json',
dependencyScanningHeadPath: 'dss_head.json',
dastHeadPath: 'dast_head.json',
sastContainerHeadPath: 'sast_container_head.json',
sastHelpPath: 'path',
dependencyScanningHelpPath: 'path',
vulnerabilityFeedbackPath: 'vulnerability_feedback_path.json',
vulnerabilityFeedbackHelpPath: 'path',
dastHelpPath: 'path',
sastContainerHelpPath: 'path',
pipelineId: 123,
canCreateIssue: true,
canCreateMergeRequest: true,
canDismissVulnerability: true,
},
});
});
it('renders loading summary text + spinner', done => {
expect(vm.$el.querySelector('.gl-spinner')).not.toBeNull();
expect(vm.$el.textContent).toContain('SAST is loading');
expect(vm.$el.textContent).toContain('Dependency scanning is loading');
expect(vm.$el.textContent).toContain('Container scanning is loading');
expect(vm.$el.textContent).toContain('DAST is loading');
setTimeout(() => {
done();
}, 0);
});
});
describe('with all reports', () => {
beforeEach(() => {
mock.onGet('sast_head.json').reply(200, sastIssues);
mock.onGet('dss_head.json').reply(200, sastIssues);
mock.onGet('dast_head.json').reply(200, dast);
mock.onGet('sast_container_head.json').reply(200, dockerReport);
mock.onGet('vulnerability_feedback_path.json').reply(200, []);
vm = mountComponentWithStore(Component, {
store: createStore(),
props: {
headBlobPath: 'path',
sastHeadPath: 'sast_head.json',
dependencyScanningHeadPath: 'dss_head.json',
dastHeadPath: 'dast_head.json',
sastContainerHeadPath: 'sast_container_head.json',
sastHelpPath: 'path',
dependencyScanningHelpPath: 'path',
vulnerabilityFeedbackPath: 'vulnerability_feedback_path.json',
vulnerabilityFeedbackHelpPath: 'path',
dastHelpPath: 'path',
sastContainerHelpPath: 'path',
pipelineId: 123,
canCreateIssue: true,
canCreateMergeRequest: true,
canDismissVulnerability: true,
},
});
});
it('renders reports', done => {
setTimeout(() => {
expect(vm.$el.querySelector('.gl-spinner')).toBeNull();
expect(vm.$el.textContent).toContain('SAST detected 3 vulnerabilities');
expect(vm.$el.textContent).toContain('Dependency scanning detected 3 vulnerabilities');
// Renders container scanning result
expect(vm.$el.textContent).toContain('Container scanning detected 2 vulnerabilities');
// Renders DAST result
expect(vm.$el.textContent).toContain('DAST detected 2 vulnerabilities');
expect(vm.$el.textContent).not.toContain('for the source branch only');
done();
}, 0);
});
it('renders all reports collapsed by default', done => {
setTimeout(() => {
expect(vm.$el.querySelector('.gl-spinner')).toBeNull();
expect(vm.$el.querySelector('.js-collapse-btn').textContent.trim()).toEqual('Expand');
const reports = vm.$el.querySelectorAll('.js-report-section-container');
reports.forEach(report => {
expect(report).toHaveCss({ display: 'none' });
});
done();
}, 0);
});
it('renders all reports expanded with the option always-open', done => {
vm.alwaysOpen = true;
setTimeout(() => {
expect(vm.$el.querySelector('.gl-spinner')).toBeNull();
expect(vm.$el.querySelector('.js-collapse-btn')).toBeNull();
const reports = vm.$el.querySelectorAll('.js-report-section-container');
reports.forEach(report => {
expect(report).not.toHaveCss({ display: 'none' });
});
done();
}, 0);
});
});
describe('with error', () => {
beforeEach(() => {
mock.onGet('sast_head.json').reply(500);
mock.onGet('dss_head.json').reply(500);
mock.onGet('dast_head.json').reply(500);
mock.onGet('sast_container_head.json').reply(500);
mock.onGet('vulnerability_feedback_path.json').reply(500, []);
vm = mountComponentWithStore(Component, {
store: createStore(),
props: {
headBlobPath: 'path',
sastHeadPath: 'sast_head.json',
dependencyScanningHeadPath: 'dss_head.json',
dastHeadPath: 'dast_head.json',
sastContainerHeadPath: 'sast_container_head.json',
sastHelpPath: 'path',
dependencyScanningHelpPath: 'path',
vulnerabilityFeedbackPath: 'vulnerability_feedback_path.json',
vulnerabilityFeedbackHelpPath: 'path',
dastHelpPath: 'path',
sastContainerHelpPath: 'path',
pipelineId: 123,
canCreateIssue: true,
canCreateMergeRequest: true,
canDismissVulnerability: true,
},
});
});
it('renders error state', done => {
setTimeout(() => {
expect(vm.$el.querySelector('.gl-spinner')).toBeNull();
expect(vm.$el.textContent).toContain('SAST: Loading resulted in an error');
expect(vm.$el.textContent).toContain('Dependency scanning: Loading resulted in an error');
expect(vm.$el.textContent).toContain('Container scanning: Loading resulted in an error');
expect(vm.$el.textContent).toContain('DAST: Loading resulted in an error');
done();
}, 0);
});
});
});
......@@ -21322,14 +21322,6 @@ msgstr ""
msgid "ciReport|%{reportType} %{status} detected no vulnerabilities for the source branch only"
msgstr ""
msgid "ciReport|%{reportType} detected %{vulnerabilityCount} vulnerability"
msgid_plural "ciReport|%{reportType} detected %{vulnerabilityCount} vulnerabilities"
msgstr[0] ""
msgstr[1] ""
msgid "ciReport|%{reportType} detected no vulnerabilities"
msgstr ""
msgid "ciReport|%{reportType} is loading"
msgstr ""
......@@ -21489,18 +21481,6 @@ msgstr ""
msgid "ciReport|There was an error dismissing the vulnerability. Please try again."
msgstr ""
msgid "ciReport|There was an error loading DAST report"
msgstr ""
msgid "ciReport|There was an error loading SAST report"
msgstr ""
msgid "ciReport|There was an error loading container scanning report"
msgstr ""
msgid "ciReport|There was an error loading dependency scanning report"
msgstr ""
msgid "ciReport|There was an error reverting the dismissal. Please try again."
msgstr ""
......
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