Commit 18937395 authored by Kushal Pandya's avatar Kushal Pandya

Merge branch 'djadmin-site-profile-form-auth-integration' into 'master'

Add additional fields to DAST Site Profile Form

See merge request gitlab-org/gitlab!49812
parents fcd8d219 28418db9
<script>
import { isEqual } from 'lodash';
import { GlAlert, GlButton, GlForm, GlFormGroup, GlFormInput, GlModal } from '@gitlab/ui';
import {
GlAlert,
GlButton,
GlForm,
GlFormGroup,
GlFormInput,
GlModal,
GlFormTextarea,
} from '@gitlab/ui';
import { initFormField } from 'ee/security_configuration/utils';
import * as Sentry from '~/sentry/wrapper';
import { __, s__ } from '~/locale';
import { redirectTo } from '~/lib/utils/url_utility';
import { serializeFormObject } from '~/lib/utils/forms';
import validation from '~/vue_shared/directives/validation';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
import DastSiteAuthSection from './dast_site_auth_section.vue';
import dastSiteProfileCreateMutation from '../graphql/dast_site_profile_create.mutation.graphql';
import dastSiteProfileUpdateMutation from '../graphql/dast_site_profile_update.mutation.graphql';
......@@ -19,10 +29,13 @@ export default {
GlFormGroup,
GlFormInput,
GlModal,
GlFormTextarea,
DastSiteAuthSection,
},
directives: {
validation: validation(),
},
mixins: [glFeatureFlagsMixin()],
props: {
fullPath: {
type: String,
......@@ -39,7 +52,8 @@ export default {
},
},
data() {
const { name = '', targetUrl = '' } = this.siteProfile || {};
const { name = '', targetUrl = '', excludedUrls = '', requestHeaders = '' } =
this.siteProfile || {};
const form = {
state: false,
......@@ -47,11 +61,18 @@ export default {
fields: {
profileName: initFormField({ value: name }),
targetUrl: initFormField({ value: targetUrl }),
excludedUrls: initFormField({ value: excludedUrls, required: false, skipValidation: true }),
requestHeaders: initFormField({
value: requestHeaders,
required: false,
skipValidation: true,
}),
},
};
return {
form,
authSection: {},
initialFormValues: serializeFormObject(form.fields),
isLoading: false,
hasAlert: false,
......@@ -94,9 +115,13 @@ export default {
},
methods: {
onSubmit() {
const isAuthEnabled =
this.glFeatures.securityDastSiteProfilesAdditionalFields &&
this.authSection.fields.authEnabled.value;
this.form.showValidation = true;
if (!this.form.state) {
if (!this.form.state || (isAuthEnabled && !this.authSection.state)) {
return;
}
......@@ -109,6 +134,7 @@ export default {
fullPath: this.fullPath,
...(this.isEdit ? { id: this.siteProfile.id } : {}),
...serializeFormObject(this.form.fields),
...(isAuthEnabled ? serializeFormObject(this.authSection.fields) : {}),
},
};
......@@ -200,7 +226,7 @@ export default {
/>
</gl-form-group>
<hr />
<hr class="gl-border-gray-100" />
<gl-form-group
data-testid="target-url-input-group"
......@@ -219,23 +245,55 @@ export default {
/>
</gl-form-group>
<hr />
<div v-if="glFeatures.securityDastSiteProfilesAdditionalFields" class="row">
<gl-form-group
:label="s__('DastProfiles|Excluded URLs (Optional)')"
:invalid-feedback="form.fields.excludedUrls.feedback"
class="col-md-6"
>
<gl-form-textarea
v-model="form.fields.excludedUrls.value"
data-testid="excluded-urls-input"
/>
</gl-form-group>
<div class="gl-mt-6 gl-pt-6">
<gl-button
type="submit"
variant="success"
class="js-no-auto-disable"
data-testid="dast-site-profile-form-submit-button"
:loading="isLoading"
<gl-form-group
:label="s__('DastProfiles|Additional request headers (Optional)')"
:invalid-feedback="form.fields.requestHeaders.feedback"
class="col-md-6"
>
{{ s__('DastProfiles|Save profile') }}
</gl-button>
<gl-button data-testid="dast-site-profile-form-cancel-button" @click="onCancelClicked">
{{ __('Cancel') }}
</gl-button>
<gl-form-textarea
v-model="form.fields.requestHeaders.value"
data-testid="request-headers-input"
/>
</gl-form-group>
</div>
<dast-site-auth-section
v-if="glFeatures.securityDastSiteProfilesAdditionalFields"
v-model="authSection"
:show-validation="form.showValidation"
/>
<hr class="gl-border-gray-100" />
<gl-button
type="submit"
variant="success"
class="js-no-auto-disable"
data-testid="dast-site-profile-form-submit-button"
:loading="isLoading"
>
{{ s__('DastProfiles|Save profile') }}
</gl-button>
<gl-button
class="gl-ml-2"
data-testid="dast-site-profile-form-cancel-button"
@click="onCancelClicked"
>
{{ __('Cancel') }}
</gl-button>
<gl-modal
:ref="$options.modalId"
:modal-id="$options.modalId"
......
......@@ -3,7 +3,10 @@
module Projects
module Security
class DastSiteProfilesController < Projects::ApplicationController
before_action :authorize_read_on_demand_scans!
before_action do
authorize_read_on_demand_scans!
push_frontend_feature_flag(:security_dast_site_profiles_additional_fields, @project, default_enabled: :yaml)
end
feature_category :dynamic_application_security_testing
......
......@@ -5,6 +5,7 @@ import merge from 'lodash/merge';
import { createMockClient } from 'mock-apollo-client';
import VueApollo from 'vue-apollo';
import DastSiteProfileForm from 'ee/security_configuration/dast_site_profiles_form/components/dast_site_profile_form.vue';
import DastSiteAuthSection from 'ee/security_configuration/dast_site_profiles_form/components/dast_site_auth_section.vue';
import dastSiteProfileCreateMutation from 'ee/security_configuration/dast_site_profiles_form/graphql/dast_site_profile_create.mutation.graphql';
import dastSiteProfileUpdateMutation from 'ee/security_configuration/dast_site_profiles_form/graphql/dast_site_profile_update.mutation.graphql';
import { siteProfiles } from 'ee_jest/on_demand_scans/mocks/mock_data';
......@@ -21,6 +22,8 @@ const fullPath = 'group/project';
const profilesLibraryPath = `${TEST_HOST}/${fullPath}/-/security/configuration/dast_profiles`;
const profileName = 'My DAST site profile';
const targetUrl = 'http://example.com';
const excludedUrls = 'http://example.com/logout';
const requestHeaders = 'my-new-header=something';
const defaultProps = {
profilesLibraryPath,
......@@ -43,6 +46,9 @@ describe('DastSiteProfileForm', () => {
const findByTestId = testId => wrapper.find(`[data-testid="${testId}"]`);
const findProfileNameInput = () => findByTestId('profile-name-input');
const findTargetUrlInput = () => findByTestId('target-url-input');
const findAuthSection = () => wrapper.find(DastSiteAuthSection);
const findExcludedUrlsInput = () => findByTestId('excluded-urls-input');
const findRequestHeadersInput = () => findByTestId('request-headers-input');
const findSubmitButton = () => findByTestId('dast-site-profile-form-submit-button');
const findCancelButton = () => findByTestId('dast-site-profile-form-cancel-button');
const findCancelModal = () => wrapper.find(GlModal);
......@@ -88,6 +94,11 @@ describe('DastSiteProfileForm', () => {
{},
{
propsData: defaultProps,
provide: {
glFeatures: {
securityDastSiteProfilesAdditionalFields: true,
},
},
},
options,
{
......@@ -132,6 +143,18 @@ describe('DastSiteProfileForm', () => {
});
});
describe('additional fields', () => {
beforeEach(() => {
createFullComponent();
});
it('should render correctly', () => {
expect(findAuthSection().exists()).toBe(true);
expect(findExcludedUrlsInput().exists()).toBe(true);
expect(findRequestHeadersInput().exists()).toBe(true);
});
});
describe.each`
title | siteProfile | mutationVars | mutationKind
${'New site profile'} | ${null} | ${{}} | ${'dastSiteProfileCreate'}
......@@ -159,6 +182,8 @@ describe('DastSiteProfileForm', () => {
const fillAndSubmitForm = async () => {
await setFieldValue(findProfileNameInput(), profileName);
await setFieldValue(findTargetUrlInput(), targetUrl);
await setFieldValue(findExcludedUrlsInput(), excludedUrls);
await setFieldValue(findRequestHeadersInput(), requestHeaders);
submitForm();
};
......@@ -176,6 +201,8 @@ describe('DastSiteProfileForm', () => {
input: {
profileName,
targetUrl,
excludedUrls,
requestHeaders,
fullPath,
...mutationVars,
},
......@@ -266,4 +293,22 @@ describe('DastSiteProfileForm', () => {
});
});
});
describe('when feature flag is off', () => {
beforeEach(() => {
createFullComponent({
provide: {
glFeatures: {
securityDastSiteProfilesAdditionalFields: false,
},
},
});
});
it('should not render additional fields', () => {
expect(findAuthSection().exists()).toBe(false);
expect(findExcludedUrlsInput().exists()).toBe(false);
expect(findRequestHeadersInput().exists()).toBe(false);
});
});
});
......@@ -8617,6 +8617,9 @@ msgstr ""
msgid "DastProfiles|Active"
msgstr ""
msgid "DastProfiles|Additional request headers (Optional)"
msgstr ""
msgid "DastProfiles|Are you sure you want to delete this profile?"
msgstr ""
......@@ -8686,6 +8689,9 @@ msgstr ""
msgid "DastProfiles|Excluded URLs"
msgstr ""
msgid "DastProfiles|Excluded URLs (Optional)"
msgstr ""
msgid "DastProfiles|Hide debug messages"
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