Automatically select DAST profile

When there is only a single profile available in an on-demand scan's
profile selector, it is automatically selected to save the user some
clicks and to prevent potential confusion.
parent f64a7c35
......@@ -30,7 +30,7 @@ import ProfileSelectorSummaryCell from './profile_selector/summary_cell.vue';
import ScannerProfileSelector from './profile_selector/scanner_profile_selector.vue';
import SiteProfileSelector from './profile_selector/site_profile_selector.vue';
const createProfilesApolloOptions = (name, { fetchQuery, fetchError }) => ({
const createProfilesApolloOptions = (name, field, { fetchQuery, fetchError }) => ({
query: fetchQuery,
variables() {
return {
......@@ -39,6 +39,9 @@ const createProfilesApolloOptions = (name, { fetchQuery, fetchError }) => ({
},
update(data) {
const edges = data?.project?.[name]?.edges ?? [];
if (edges.length === 1) {
this[field] = edges[0].node.id;
}
return edges.map(({ node }) => node);
},
error(e) {
......@@ -66,8 +69,16 @@ export default {
},
mixins: [glFeatureFlagsMixin()],
apollo: {
scannerProfiles: createProfilesApolloOptions('scannerProfiles', SCANNER_PROFILES_QUERY),
siteProfiles: createProfilesApolloOptions('siteProfiles', SITE_PROFILES_QUERY),
scannerProfiles: createProfilesApolloOptions(
'scannerProfiles',
'selectedScannerProfileId',
SCANNER_PROFILES_QUERY,
),
siteProfiles: createProfilesApolloOptions(
'siteProfiles',
'selectedSiteProfileId',
SITE_PROFILES_QUERY,
),
},
props: {
helpPagePath: {
......@@ -104,8 +115,8 @@ export default {
return {
scannerProfiles: [],
siteProfiles: [],
selectedScannerProfile: null,
selectedSiteProfile: null,
selectedScannerProfileId: null,
selectedSiteProfileId: null,
loading: false,
errorType: null,
errors: [],
......@@ -113,6 +124,16 @@ export default {
};
},
computed: {
selectedScannerProfile() {
return this.selectedScannerProfileId
? this.scannerProfiles.find(({ id }) => id === this.selectedScannerProfileId)
: null;
},
selectedSiteProfile() {
return this.selectedSiteProfileId
? this.siteProfiles.find(({ id }) => id === this.selectedSiteProfileId)
: null;
},
errorMessage() {
return ERROR_MESSAGES[this.errorType] || null;
},
......@@ -238,37 +259,37 @@ export default {
</template>
<template v-else-if="!failedToLoadProfiles">
<scanner-profile-selector
v-model="selectedScannerProfile"
v-model="selectedScannerProfileId"
class="gl-mb-5"
:profiles="scannerProfiles"
>
<template #summary="{ profile }">
<template v-if="selectedScannerProfile" #summary>
<div class="row">
<profile-selector-summary-cell
:class="{ 'gl-text-red-500': hasProfilesConflict }"
:label="s__('DastProfiles|Scan mode')"
:value="$options.SCAN_TYPE_LABEL[profile.scanType]"
:value="$options.SCAN_TYPE_LABEL[selectedScannerProfile.scanType]"
/>
</div>
<div class="row">
<profile-selector-summary-cell
:label="s__('DastProfiles|Spider timeout')"
:value="n__('%d minute', '%d minutes', profile.spiderTimeout)"
:value="n__('%d minute', '%d minutes', selectedScannerProfile.spiderTimeout)"
/>
<profile-selector-summary-cell
:label="s__('DastProfiles|Target timeout')"
:value="n__('%d second', '%d seconds', profile.targetTimeout)"
:value="n__('%d second', '%d seconds', selectedScannerProfile.targetTimeout)"
/>
</div>
<div class="row">
<profile-selector-summary-cell
:label="s__('DastProfiles|AJAX spider')"
:value="profile.useAjaxSpider ? __('On') : __('Off')"
:value="selectedScannerProfile.useAjaxSpider ? __('On') : __('Off')"
/>
<profile-selector-summary-cell
:label="s__('DastProfiles|Debug messages')"
:value="
profile.showDebugMessages
selectedScannerProfile.showDebugMessages
? s__('DastProfiles|Show debug messages')
: s__('DastProfiles|Hide debug messages')
"
......@@ -276,13 +297,17 @@ export default {
</div>
</template>
</scanner-profile-selector>
<site-profile-selector v-model="selectedSiteProfile" class="gl-mb-5" :profiles="siteProfiles">
<template #summary="{ profile }">
<site-profile-selector
v-model="selectedSiteProfileId"
class="gl-mb-5"
:profiles="siteProfiles"
>
<template v-if="selectedSiteProfile" #summary>
<div class="row">
<profile-selector-summary-cell
:class="{ 'gl-text-red-500': hasProfilesConflict }"
:label="s__('DastProfiles|Target URL')"
:value="profile.targetUrl"
:value="selectedSiteProfile.targetUrl"
/>
</div>
</template>
......
......@@ -25,14 +25,14 @@ export default {
default: () => [],
},
value: {
type: Object,
type: String,
required: false,
default: null,
},
},
methods: {
isChecked({ id }) {
return this.value?.id === id;
computed: {
selectedProfile() {
return this.value ? this.profiles.find(({ id }) => this.value === id) : null;
},
},
};
......@@ -67,7 +67,9 @@ export default {
</template>
<gl-dropdown
:text="
value ? value.dropdownLabel : s__('OnDemandScans|Select one of the existing profiles')
selectedProfile
? selectedProfile.dropdownLabel
: s__('OnDemandScans|Select one of the existing profiles')
"
class="mw-460"
data-testid="profiles-dropdown"
......@@ -75,9 +77,9 @@ export default {
<gl-dropdown-item
v-for="profile in profiles"
:key="profile.id"
:is-checked="isChecked(profile)"
:is-checked="value === profile.id"
is-check-item
@click="$emit('input', profile)"
@click="$emit('input', profile.id)"
>
{{ profile.profileName }}
</gl-dropdown-item>
......@@ -87,7 +89,7 @@ export default {
data-testid="selected-profile-summary"
class="gl-mt-6 gl-pt-6 gl-border-t-solid gl-border-gray-100 gl-border-t-1"
>
<slot name="summary" :profile="value"></slot>
<slot name="summary"></slot>
</div>
</gl-form-group>
<template v-else>
......
......@@ -57,8 +57,8 @@ export default {
)
}}</template>
<template #new-profile>{{ s__('OnDemandScans|Create a new scanner profile') }}</template>
<template #summary="{ profile }">
<slot name="summary" :profile="profile"></slot>
<template #summary>
<slot name="summary"></slot>
</template>
</profile-selector>
</template>
......@@ -60,8 +60,8 @@ export default {
)
}}</template>
<template #new-profile>{{ s__('OnDemandScans|Create a new site profile') }}</template>
<template #summary="{ profile }">
<slot name="summary" :profile="profile"></slot>
<template #summary>
<slot name="summary"></slot>
</template>
</profile-selector>
</template>
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