diff --git a/app/assets/javascripts/ide/components/new_dropdown/modal.vue b/app/assets/javascripts/ide/components/new_dropdown/modal.vue index b62959288ee7684eee86abbce65faab627d8f273..4766a2fe6ae0765efac5ed9666a69e9b215b04f1 100644 --- a/app/assets/javascripts/ide/components/new_dropdown/modal.vue +++ b/app/assets/javascripts/ide/components/new_dropdown/modal.vue @@ -4,6 +4,7 @@ import flash from '~/flash'; import { __, sprintf, s__ } from '~/locale'; import { GlModal } from '@gitlab/ui'; import { modalTypes } from '../../constants'; +import { trimPathComponents } from '../../utils'; export default { components: { @@ -51,6 +52,8 @@ export default { methods: { ...mapActions(['createTempEntry', 'renameEntry']), submitForm() { + this.entryName = trimPathComponents(this.entryName); + if (this.modalType === modalTypes.rename) { if (this.entries[this.entryName] && !this.entries[this.entryName].deleted) { flash( diff --git a/app/assets/javascripts/ide/utils.js b/app/assets/javascripts/ide/utils.js index e7615be498bbe1656ef49f6657857df1f3c670d0..1ea2b199237e5d9f5bc3429b7841d34e9bb8bf7d 100644 --- a/app/assets/javascripts/ide/utils.js +++ b/app/assets/javascripts/ide/utils.js @@ -69,6 +69,12 @@ export const createPathWithExt = p => { return `${p.substring(1, p.lastIndexOf('.') + 1 || p.length)}${ext || '.js'}`; }; +export const trimPathComponents = path => + path + .split('/') + .map(s => s.trim()) + .join('/'); + export function registerLanguages(def, ...defs) { if (defs.length) defs.forEach(lang => registerLanguages(lang)); diff --git a/changelogs/unreleased/216509-ide-new-file-trim.yml b/changelogs/unreleased/216509-ide-new-file-trim.yml new file mode 100644 index 0000000000000000000000000000000000000000..ca7e6cc2eb3ef5bf5de299159fdfb85ea0721752 --- /dev/null +++ b/changelogs/unreleased/216509-ide-new-file-trim.yml @@ -0,0 +1,5 @@ +--- +title: Trim whitespace in directory names in the Web IDE +merge_request: 31305 +author: +type: fixed diff --git a/spec/frontend/ide/components/new_dropdown/modal_spec.js b/spec/frontend/ide/components/new_dropdown/modal_spec.js index b6d4e60ce347209b86b5eda9820394db98b66df0..62a59a76bf4326cededf06f1cc11e784cfbaf61c 100644 --- a/spec/frontend/ide/components/new_dropdown/modal_spec.js +++ b/spec/frontend/ide/components/new_dropdown/modal_spec.js @@ -122,9 +122,9 @@ describe('new file modal component', () => { describe('submitForm', () => { let store; + beforeEach(() => { store = createStore(); - store.state.entries = { 'test-path/test': { name: 'test', @@ -161,5 +161,15 @@ describe('new file modal component', () => { expect(createFlash).not.toHaveBeenCalled(); }); + + it('removes leading/trailing found in the new name', () => { + vm.open('rename', 'test-path/test'); + + vm.entryName = 'test-path /test'; + + vm.submitForm(); + + expect(vm.entryName).toBe('test-path/test'); + }); }); }); diff --git a/spec/frontend/ide/utils_spec.js b/spec/frontend/ide/utils_spec.js index 10a31842dd4a059860b5e115b516d8fdadbba29e..ea975500e8da0e697e024c510ec4b8399515bcce 100644 --- a/spec/frontend/ide/utils_spec.js +++ b/spec/frontend/ide/utils_spec.js @@ -1,5 +1,5 @@ import { commitItemIconMap } from '~/ide/constants'; -import { getCommitIconMap, isTextFile, registerLanguages } from '~/ide/utils'; +import { getCommitIconMap, isTextFile, registerLanguages, trimPathComponents } from '~/ide/utils'; import { decorateData } from '~/ide/stores/utils'; import { languages } from 'monaco-editor'; @@ -104,6 +104,21 @@ describe('WebIDE utils', () => { }); }); + describe('trimPathComponents', () => { + it.each` + input | output + ${'example path '} | ${'example path'} + ${'p/somefile '} | ${'p/somefile'} + ${'p /somefile '} | ${'p/somefile'} + ${'p/ somefile '} | ${'p/somefile'} + ${' p/somefile '} | ${'p/somefile'} + ${'p/somefile .md'} | ${'p/somefile .md'} + ${'path / to / some/file.doc '} | ${'path/to/some/file.doc'} + `('trims all path components in path: "$input"', ({ input, output }) => { + expect(trimPathComponents(input)).toEqual(output); + }); + }); + describe('registerLanguages', () => { let langs;