diff --git a/webapp/components/_new/features/MySomethingList/MySomethingList.spec.js b/webapp/components/_new/features/MySomethingList/MySomethingList.spec.js index ea19bce8c..0cc99c467 100644 --- a/webapp/components/_new/features/MySomethingList/MySomethingList.spec.js +++ b/webapp/components/_new/features/MySomethingList/MySomethingList.spec.js @@ -8,12 +8,16 @@ const localVue = global.localVue describe('MySomethingList.vue', () => { let wrapper + let data let mocks let getters const socialMediaUrl = 'https://freeradical.zone/@mattwr18' - const newSocialMediaUrl = 'https://twitter.com/mattwr18' + // const newSocialMediaUrl = 'https://twitter.com/mattwr18' beforeEach(() => { + data = () => { + return {} + } mocks = { $t: jest.fn(), $apollo: { @@ -32,69 +36,75 @@ describe('MySomethingList.vue', () => { }) describe('mount', () => { - let form, input, slots, submitButton + // Wolle let form, input, slots, submitButton + let slots const Wrapper = () => { const store = new Vuex.Store({ getters, }) slots = { 'list-item': '
' } - return mount(MySomethingList, { store, mocks, localVue, slots }) + return mount(MySomethingList, { data, store, mocks, localVue, slots }) } - describe('adding social media link', () => { - beforeEach(() => { - wrapper = Wrapper() - form = wrapper.find('form') - input = wrapper.find('input#addSocialMedia') - submitButton = wrapper.find('button') - }) + // describe('adding social media link', () => { + // beforeEach(async () => { + // wrapper = Wrapper() + // form = wrapper.find('form') + // form.trigger('submit') + // await Vue.nextTick() + // console.log(wrapper.html()) + // console.log('wrapper.vm.socialMediaLinks: ', wrapper.vm.socialMediaLinks) + // input = wrapper.find('input#editSocialMedia') + // console.log('input: ', input) + // submitButton = wrapper.find('button') + // }) - // Wolle it('requires the link to be a valid url', async () => { - // input.setValue('some value') - // form.trigger('submit') - // await Vue.nextTick() - // expect(mocks.$apollo.mutate).not.toHaveBeenCalled() - // }) + // Wolle it('requires the link to be a valid url', async () => { + // input.setValue('some value') + // form.trigger('submit') + // await Vue.nextTick() + // expect(mocks.$apollo.mutate).not.toHaveBeenCalled() + // }) - it('displays an error message when not saved successfully', async () => { - mocks.$apollo.mutate.mockRejectedValue({ message: 'Ouch!' }) - input.setValue(newSocialMediaUrl) - form.trigger('submit') - await Vue.nextTick() - await flushPromises() - expect(mocks.$toast.error).toHaveBeenCalledTimes(1) - }) + // Wolle it('displays an error message when not saved successfully', async () => { + // mocks.$apollo.mutate.mockRejectedValue({ message: 'Ouch!' }) + // input.setValue(newSocialMediaUrl) + // form.trigger('submit') + // await Vue.nextTick() + // await flushPromises() + // expect(mocks.$toast.error).toHaveBeenCalledTimes(1) + // }) - describe('success', () => { - beforeEach(async () => { - mocks.$apollo.mutate.mockResolvedValue({ - data: { CreateSocialMedia: { id: 's2', url: newSocialMediaUrl } }, - }) - input.setValue(newSocialMediaUrl) - form.trigger('submit') - await Vue.nextTick() - }) + // describe('success', () => { + // beforeEach(async () => { + // mocks.$apollo.mutate.mockResolvedValue({ + // data: { CreateSocialMedia: { id: 's2', url: newSocialMediaUrl } }, + // }) + // input.setValue(newSocialMediaUrl) + // form.trigger('submit') + // await Vue.nextTick() + // }) - it('sends the new url to the backend', () => { - const expected = expect.objectContaining({ - variables: { url: newSocialMediaUrl }, - }) + // it('sends the new url to the backend', () => { + // const expected = expect.objectContaining({ + // variables: { url: newSocialMediaUrl }, + // }) - expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) - }) + // expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) + // }) - it('displays a success message', async () => { - await flushPromises() - expect(mocks.$toast.success).toHaveBeenCalledTimes(1) - }) + // it('displays a success message', async () => { + // await flushPromises() + // expect(mocks.$toast.success).toHaveBeenCalledTimes(1) + // }) - it('clears the form', async () => { - await flushPromises() - expect(input.value).toBe(undefined) - expect(submitButton.vm.$attrs.disabled).toBe(true) - }) - }) - }) + // it('clears the form', async () => { + // await flushPromises() + // expect(input.value).toBe(undefined) + // expect(submitButton.vm.$attrs.disabled).toBe(true) + // }) + // }) + // }) describe('given existing social media links', () => { beforeEach(() => { @@ -103,9 +113,14 @@ describe('MySomethingList.vue', () => { socialMedia: [{ id: 's1', url: socialMediaUrl }], }), } - + // Wolle propsData = { editingLink: { id: 's1', url: socialMediaUrl } } + // data = () => { + // return { + // editingLink: { id: 's2', url: socialMediaUrl }, + // } + // } wrapper = Wrapper() - form = wrapper.find('form') + // form = wrapper.find('form') }) describe('for each item it', () => { @@ -122,44 +137,47 @@ describe('MySomethingList.vue', () => { }) }) - it('does not accept a duplicate url', async () => { - wrapper.find('input#addSocialMedia').setValue(socialMediaUrl) - form.trigger('submit') - await Vue.nextTick() - expect(mocks.$apollo.mutate).not.toHaveBeenCalled() - }) + // Wolle it('does not accept a duplicate url', async () => { + // // wrapper.find('input#addSocialMedia').setValue(socialMediaUrl) + // wrapper.find('input#editSocialMedia').setValue(socialMediaUrl) + // form.trigger('submit') + // await Vue.nextTick() + // expect(mocks.$apollo.mutate).not.toHaveBeenCalled() + // }) - describe('editing social media link', () => { - beforeEach(async () => { - const editButton = wrapper.find('.base-button[data-test="edit-button"]') - editButton.trigger('click') - await Vue.nextTick() - input = wrapper.find('input#editSocialMedia') - }) + // describe('editing social media link', () => { + // beforeEach(async () => { + // const editButton = wrapper.find('.base-button[data-test="edit-button"]') + // editButton.trigger('click') + // await Vue.nextTick() + // input = wrapper.find('input#editSocialMedia') + // }) - it('disables adding new links while editing', () => { - const addInput = wrapper.find('input#addSocialMedia') + // it('disables adding new links while editing', () => { + // const addInput = wrapper.find('input#addSocialMedia') + // wrapper.find('.base-button[data-test="add-save-button"]').text(). + // expect(addInput.exists()).toBe(false) + // const submitButton = wrapper.find('.base-button[data-test="add-save-button"]') + // expect(submitButton.text()).not.toContain('settings.social-media.submit') + // }) - expect(addInput.exists()).toBe(false) - }) + // Wolle remove? or test here abstract? it('sends the new url to the backend', async () => { + // const expected = expect.objectContaining({ + // variables: { id: 's1', url: newSocialMediaUrl }, + // }) + // input.setValue(newSocialMediaUrl) + // form.trigger('submit') + // await Vue.nextTick() + // expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) + // }) - // Wolle remove? or test here abstract? it('sends the new url to the backend', async () => { - // const expected = expect.objectContaining({ - // variables: { id: 's1', url: newSocialMediaUrl }, - // }) - // input.setValue(newSocialMediaUrl) - // form.trigger('submit') - // await Vue.nextTick() - // expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) - // }) - - it('allows the user to cancel editing', async () => { - const cancelButton = wrapper.find('button#cancel') - cancelButton.trigger('click') - await Vue.nextTick() - expect(wrapper.find('input#editSocialMedia').exists()).toBe(false) - }) - }) + // it('allows the user to cancel editing', async () => { + // const cancelButton = wrapper.find('button#cancel') + // cancelButton.trigger('click') + // await Vue.nextTick() + // expect(wrapper.find('input#editSocialMedia').exists()).toBe(false) + // }) + // }) describe('deleting social media link', () => { beforeEach(async () => { diff --git a/webapp/components/_new/features/MySomethingList/MySomethingList.vue b/webapp/components/_new/features/MySomethingList/MySomethingList.vue index 55c9f0808..944ac41f3 100644 --- a/webapp/components/_new/features/MySomethingList/MySomethingList.vue +++ b/webapp/components/_new/features/MySomethingList/MySomethingList.vue @@ -8,11 +8,15 @@ @input-valid="handleInputValid" @submit="handleSubmitSocialMedia" > -
+
- {{ /* $t('settings.social-media.name') */ 'Edit "' + editingLink.url + '"' }} + {{ + /* $t('settings.social-media.name') */ editingLink.id === '' + ? 'Add new one' + : 'Edit "' + editingLink.url + '"' + }} @@ -61,18 +65,23 @@
- + /> --> - - {{ editingLink.id ? $t('actions.save') : $t('settings.social-media.submit') }} + + {{ isEditing ? $t('actions.save') : $t('settings.social-media.submit') }} - + {{ $t('actions.cancel') }} @@ -112,13 +121,19 @@ export default { formData: this.useFormData, formSchema: this.useFormSchema, disabled: true, - editingLink: {}, + editingLink: null, } }, computed: { ...mapGetters({ currentUser: 'auth/user', }), + isEditing() { + return this.editingLink !== null + }, + isCreation() { + return this.editingLink !== null && this.editingLink.id === '' + }, socialMediaLinks() { const domainRegex = /^(?:https?:\/\/)?(?:[^@\n])?(?:www\.)?([^:/\n?]+)/g const { socialMedia = [] } = this.currentUser @@ -134,7 +149,7 @@ export default { setCurrentUser: 'auth/SET_USER', }), handleCancel() { - this.editingLink = {} + this.editingLink = null this.formData.socialMediaUrl = '' this.disabled = true }, @@ -183,57 +198,69 @@ export default { } }, async handleSubmitSocialMedia() { - const isEditing = !!this.editingLink.id - const url = this.formData.socialMediaUrl + // Wolle const isEditing = (this.editingLink !== null) + if (!this.isEditing) { + // Wolle this.editingLink = { id: '', url: '' } + this.handleEditSocialMedia({ id: '', url: '' }) + } else { + // Wolle const url = this.formData.socialMediaUrl + this.editingLink.url = this.formData.socialMediaUrl - const duplicateUrl = this.socialMediaLinks.find((link) => link.url === url) - if (duplicateUrl && duplicateUrl.id !== this.editingLink.id) { - return this.$toast.error(this.$t('settings.social-media.requireUnique')) - } - - let mutation = gql` - mutation($url: String!) { - CreateSocialMedia(url: $url) { - id - url - } + const duplicateUrl = this.socialMediaLinks.find((link) => link.url === this.editingLink.url) + // Wolle console.log('duplicateUrl: ', duplicateUrl) + // console.log('this.isEditing: ', this.isEditing) + // console.log('this.editingLink: ', this.editingLink) + if (duplicateUrl && this.isEditing && duplicateUrl.id !== this.editingLink.id) { + return this.$toast.error(this.$t('settings.social-media.requireUnique')) } - ` - const variables = { url } - let successMessage = this.$t('settings.social-media.successAdd') - if (isEditing) { - mutation = gql` - mutation($id: ID!, $url: String!) { - UpdateSocialMedia(id: $id, url: $url) { - id - url + let mutation, variables, successMessage + if (this.isCreation) { + mutation = gql` + mutation($url: String!) { + CreateSocialMedia(url: $url) { + id + url + } } - } - ` - variables.id = this.editingLink.id - successMessage = this.$t('settings.data.success') - } + ` + variables = { url: this.editingLink.url } + successMessage = this.$t('settings.social-media.successAdd') + } else { + mutation = gql` + mutation($id: ID!, $url: String!) { + UpdateSocialMedia(id: $id, url: $url) { + id + url + } + } + ` + variables = { id: this.editingLink.id, url: this.editingLink.url } + successMessage = this.$t('settings.data.success') + } - try { - await this.$apollo.mutate({ - mutation, - variables, - update: (store, { data }) => { - const newSocialMedia = isEditing ? data.UpdateSocialMedia : data.CreateSocialMedia - this.setCurrentUser({ - ...this.currentUser, - socialMedia: unionBy([newSocialMedia], this.currentUser.socialMedia, 'id'), - }) - }, - }) + try { + await this.$apollo.mutate({ + mutation, + variables, + update: (_store, { data }) => { + const newSocialMedia = !this.isCreation + ? data.UpdateSocialMedia + : data.CreateSocialMedia + this.setCurrentUser({ + ...this.currentUser, + socialMedia: unionBy([newSocialMedia], this.currentUser.socialMedia, 'id'), + }) + }, + }) - this.$toast.success(successMessage) - this.formData.socialMediaUrl = '' - this.disabled = true - this.editingLink = {} - } catch (err) { - this.$toast.error(err.message) + this.$toast.success(successMessage) + this.formData.socialMediaUrl = '' + this.disabled = true + this.editingLink = null + } catch (err) { + this.$toast.error(err.message) + } } }, }, diff --git a/webapp/pages/settings/my-social-media.spec.js b/webapp/pages/settings/my-social-media.spec.js index a9d7a15d0..2da42b1d3 100644 --- a/webapp/pages/settings/my-social-media.spec.js +++ b/webapp/pages/settings/my-social-media.spec.js @@ -1,5 +1,5 @@ import { mount } from '@vue/test-utils' -// import flushPromises from 'flush-promises' +import flushPromises from 'flush-promises' import MySocialMedia from './my-social-media.vue' import Vuex from 'vuex' import Vue from 'vue' @@ -33,7 +33,7 @@ describe('my-social-media.vue', () => { }) describe('mount', () => { - // let form, input, submitButton + // Wolle let form, input, submitButton let form, input const Wrapper = () => { const store = new Vuex.Store({ @@ -43,11 +43,13 @@ describe('my-social-media.vue', () => { } describe('adding social media link', () => { - beforeEach(() => { + beforeEach(async () => { wrapper = Wrapper() form = wrapper.find('form') - input = wrapper.find('input#addSocialMedia') - // submitButton = wrapper.find('button') + form.trigger('submit') + await Vue.nextTick() + input = wrapper.find('input#editSocialMedia') + // Wolle submitButton = wrapper.find('button') }) it('requires the link to be a valid url', async () => { @@ -57,44 +59,50 @@ describe('my-social-media.vue', () => { expect(mocks.$apollo.mutate).not.toHaveBeenCalled() }) - // it('displays an error message when not saved successfully', async () => { - // mocks.$apollo.mutate.mockRejectedValue({ message: 'Ouch!' }) - // input.setValue(newSocialMediaUrl) - // form.trigger('submit') - // await Vue.nextTick() - // await flushPromises() - // expect(mocks.$toast.error).toHaveBeenCalledTimes(1) - // }) + it('displays an error message when not saved successfully', async () => { + mocks.$apollo.mutate.mockRejectedValue({ message: 'Ouch!' }) + input.setValue(newSocialMediaUrl) + form.trigger('submit') + await Vue.nextTick() + await flushPromises() + expect(mocks.$toast.error).toHaveBeenCalledTimes(1) + }) - // describe('success', () => { - // beforeEach(async () => { - // mocks.$apollo.mutate.mockResolvedValue({ - // data: { CreateSocialMedia: { id: 's2', url: newSocialMediaUrl } }, - // }) - // input.setValue(newSocialMediaUrl) - // form.trigger('submit') - // await Vue.nextTick() - // }) + describe('success', () => { + beforeEach(async () => { + mocks.$apollo.mutate.mockResolvedValue({ + data: { CreateSocialMedia: { id: 's2', url: newSocialMediaUrl } }, + }) + input.setValue(newSocialMediaUrl) + form.trigger('submit') + await Vue.nextTick() + }) - // it('sends the new url to the backend', () => { - // const expected = expect.objectContaining({ - // variables: { url: newSocialMediaUrl }, - // }) + it('sends the new url to the backend', () => { + const expected = expect.objectContaining({ + variables: { url: newSocialMediaUrl }, + }) + expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) + }) - // expect(mocks.$apollo.mutate).toHaveBeenCalledWith(expected) - // }) + it('displays a success message', async () => { + await flushPromises() + expect(mocks.$toast.success).toHaveBeenCalledTimes(1) + }) - // it('displays a success message', async () => { - // await flushPromises() - // expect(mocks.$toast.success).toHaveBeenCalledTimes(1) - // }) - - // it('clears the form', async () => { - // await flushPromises() - // expect(input.value).toBe(undefined) - // expect(submitButton.vm.$attrs.disabled).toBe(true) - // }) - // }) + // Wolle it('clears the form', async () => { + // await flushPromises() + // expect(input.value).toBe(undefined) + // expect(submitButton.vm.$attrs.disabled).toBe(true) + // }) + it('switches back to list', async () => { + await flushPromises() + // Wolle expect(input.value).toBe(undefined) + // expect(submitButton.vm.$attrs.disabled).toBe(true) + const submitButton = wrapper.find('.base-button[data-test="add-save-button"]') + expect(submitButton.text()).not.toContain('settings.social-media.submit') + }) + }) }) describe('given existing social media links', () => { @@ -127,12 +135,14 @@ describe('my-social-media.vue', () => { // }) }) - // it('does not accept a duplicate url', async () => { - // wrapper.find('input#addSocialMedia').setValue(socialMediaUrl) - // form.trigger('submit') - // await Vue.nextTick() - // expect(mocks.$apollo.mutate).not.toHaveBeenCalled() - // }) + it('does not accept a duplicate url', async () => { + form.trigger('submit') + await Vue.nextTick() + wrapper.find('input#editSocialMedia').setValue(socialMediaUrl) + form.trigger('submit') + await Vue.nextTick() + expect(mocks.$apollo.mutate).not.toHaveBeenCalled() + }) describe('editing social media link', () => { beforeEach(async () => { @@ -142,13 +152,14 @@ describe('my-social-media.vue', () => { input = wrapper.find('input#editSocialMedia') }) - // it('disables adding new links while editing', () => { - // const addInput = wrapper.find('input#addSocialMedia') + it('disables adding new links while editing', () => { + // Wolle const addInput = wrapper.find('input#addSocialMedia') + // expect(addInput.exists()).toBe(false) + const submitButton = wrapper.find('.base-button[data-test="add-save-button"]') + expect(submitButton.text()).not.toContain('settings.social-media.submit') + }) - // expect(addInput.exists()).toBe(false) - // }) - - it.only('sends the new url to the backend', async () => { + it('sends the new url to the backend', async () => { const expected = expect.objectContaining({ variables: { id: 's1', url: newSocialMediaUrl }, })