Commit 16b13f2d authored by Rajat Jain's avatar Rajat Jain

Show validation error for setting project suffix

Only lowercase alphabets, numbers, and underscores are allowed
in the project suffix.

This change will show input in error state and a supporting text
to let users know which chars are allowed.

Changelog: changed
parent 57b6e1f6
...@@ -75,6 +75,7 @@ export default { ...@@ -75,6 +75,7 @@ export default {
outgoingName: this.initialOutgoingName || __('GitLab Support Bot'), outgoingName: this.initialOutgoingName || __('GitLab Support Bot'),
projectKey: this.initialProjectKey, projectKey: this.initialProjectKey,
searchTerm: '', searchTerm: '',
projectKeyError: null,
}; };
}, },
computed: { computed: {
...@@ -104,6 +105,14 @@ export default { ...@@ -104,6 +105,14 @@ export default {
this.selectedFileTemplateProjectId = selectedFileTemplateProjectId; this.selectedFileTemplateProjectId = selectedFileTemplateProjectId;
this.selectedTemplate = selectedTemplate; this.selectedTemplate = selectedTemplate;
}, },
validateProjectKey() {
if (this.projectKey && !new RegExp(/^[a-z0-9_]+$/).test(this.projectKey)) {
this.projectKeyError = __('Only use lowercase letters, numbers, and underscores.');
return;
}
this.projectKeyError = null;
},
}, },
}; };
</script> </script>
...@@ -169,8 +178,17 @@ export default { ...@@ -169,8 +178,17 @@ export default {
v-model.trim="projectKey" v-model.trim="projectKey"
data-testid="project-suffix" data-testid="project-suffix"
class="form-control" class="form-control"
:state="!projectKeyError"
@blur="validateProjectKey"
/> />
<span v-if="hasProjectKeySupport" class="form-text text-muted"> <span v-if="hasProjectKeySupport && projectKeyError" class="form-text text-danger">
{{ projectKeyError }}
</span>
<span
v-if="hasProjectKeySupport"
class="form-text text-muted"
:class="{ 'gl-mt-2!': hasProjectKeySupport && projectKeyError }"
>
{{ __('A string appended to the project path to form the Service Desk email address.') }} {{ __('A string appended to the project path to form the Service Desk email address.') }}
</span> </span>
<span v-else class="form-text text-muted"> <span v-else class="form-text text-muted">
......
...@@ -24184,6 +24184,9 @@ msgstr "" ...@@ -24184,6 +24184,9 @@ msgstr ""
msgid "Only reCAPTCHA v2 is supported:" msgid "Only reCAPTCHA v2 is supported:"
msgstr "" msgstr ""
msgid "Only use lowercase letters, numbers, and underscores."
msgstr ""
msgid "Only users from the specified IP address ranges are able to reach this group, including all subgroups, projects, and Git repositories." msgid "Only users from the specified IP address ranges are able to reach this group, including all subgroups, projects, and Git repositories."
msgstr "" msgstr ""
......
import { GlButton, GlDropdown, GlLoadingIcon, GlToggle } from '@gitlab/ui'; import { GlButton, GlDropdown, GlLoadingIcon, GlToggle } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils'; import { shallowMount, mount } from '@vue/test-utils';
import { nextTick } from 'vue'; import { nextTick } from 'vue';
import { extendedWrapper } from 'helpers/vue_test_utils_helper'; import { extendedWrapper } from 'helpers/vue_test_utils_helper';
import ServiceDeskSetting from '~/projects/settings_service_desk/components/service_desk_setting.vue'; import ServiceDeskSetting from '~/projects/settings_service_desk/components/service_desk_setting.vue';
...@@ -16,9 +16,9 @@ describe('ServiceDeskSetting', () => { ...@@ -16,9 +16,9 @@ describe('ServiceDeskSetting', () => {
const findTemplateDropdown = () => wrapper.find(GlDropdown); const findTemplateDropdown = () => wrapper.find(GlDropdown);
const findToggle = () => wrapper.find(GlToggle); const findToggle = () => wrapper.find(GlToggle);
const createComponent = ({ props = {} } = {}) => const createComponent = ({ props = {}, mountFunction = shallowMount } = {}) =>
extendedWrapper( extendedWrapper(
shallowMount(ServiceDeskSetting, { mountFunction(ServiceDeskSetting, {
propsData: { propsData: {
isEnabled: true, isEnabled: true,
...props, ...props,
...@@ -128,6 +128,23 @@ describe('ServiceDeskSetting', () => { ...@@ -128,6 +128,23 @@ describe('ServiceDeskSetting', () => {
expect(input.exists()).toBe(true); expect(input.exists()).toBe(true);
expect(input.attributes('disabled')).toBeUndefined(); expect(input.attributes('disabled')).toBeUndefined();
}); });
it('shows error when value contains uppercase or special chars', async () => {
wrapper = createComponent({
props: { customEmailEnabled: true },
mountFunction: mount,
});
const input = wrapper.findByTestId('project-suffix');
input.setValue('abc_A.');
input.trigger('blur');
await wrapper.vm.$nextTick();
const errorText = wrapper.find('.text-danger');
expect(errorText.exists()).toBe(true);
});
}); });
describe('customEmail is the same as incomingEmail', () => { describe('customEmail is the same as incomingEmail', () => {
......
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