diff --git a/src/router.js b/src/router.js index a776084..f8cd172 100644 --- a/src/router.js +++ b/src/router.js @@ -7,7 +7,7 @@ import LoadView from '@/views/LoadView' import store from '@/store' import database from '@/lib/database' -const routes = [ +export const routes = [ { path: '/', name: 'Welcome', diff --git a/src/views/MainView/MainMenu.vue b/src/views/MainView/MainMenu.vue index 1c9b6c4..6aeb898 100644 --- a/src/views/MainView/MainMenu.vue +++ b/src/views/MainView/MainMenu.vue @@ -178,6 +178,7 @@ export default { this.openSaveModal() }, openSaveModal() { + this.$modal.hide('inquiry-conflict') this.errorMsg = null this.name = '' this.$modal.show('save') @@ -190,8 +191,6 @@ export default { this.saveInquiry() }, async saveInquiry() { - const dataSet = this.currentInquiryTab.result - const tabView = this.currentInquiryTab.view const eventName = this.currentInquiryTab.name && this.name ? 'inquiry.saveAs' diff --git a/tests/App.spec.js b/tests/App.spec.js index 76f2f60..bda6e13 100644 --- a/tests/App.spec.js +++ b/tests/App.spec.js @@ -1,13 +1,22 @@ import { expect } from 'chai' import sinon from 'sinon' -import { shallowMount } from '@vue/test-utils' +import { shallowMount, mount } from '@vue/test-utils' import { createStore } from 'vuex' import App from '@/App.vue' import storedInquiries from '@/lib/storedInquiries' +import actions from '@/store/actions' import mutations from '@/store/mutations' import { nextTick } from 'vue' +import { createRouter, createWebHistory } from 'vue-router' +import { routes } from '@/router' describe('App.vue', () => { + let clock + + beforeEach(() => { + clock = sinon.useFakeTimers() + }) + afterEach(() => { sinon.restore() }) @@ -92,4 +101,134 @@ describe('App.vue', () => { { id: 3, name: 'bar' } ]) }) + + it('Closes with saving and does not change the next tab', async () => { + const inquiries = [ + { + id: 1, + name: 'foo', + query: 'SELECT * FROM foo', + viewType: 'chart', + viewOptions: {}, + createdAt: '2020-11-07T20:57:04.492Z' + }, + { + id: 2, + name: 'bar', + query: 'SELECT * FROM bar', + viewType: 'chart', + viewOptions: {}, + createdAt: '2020-11-07T20:57:04.492Z' + } + ] + sinon.stub(storedInquiries, 'getStoredInquiries').returns(inquiries) + const tab1 = { + id: 1, + name: 'foo', + query: 'select * from foo', + viewType: 'chart', + viewOptions: {}, + layout: { + sqlEditor: 'above', + table: 'bottom', + dataView: 'hidden' + }, + result: { + columns: ['name', 'points'], + values: { + name: ['Gryffindor', 'Hufflepuff', 'Ravenclaw', 'Slytherin'], + points: [100, 90, 95, 80] + } + }, + isSaved: false + } + const tab2 = { + id: 2, + name: 'bar', + query: 'SELECT * FROM bar', + viewType: 'chart', + viewOptions: {}, + layout: { + sqlEditor: 'above', + table: 'hidden', + dataView: 'bottom' + }, + result: { + columns: ['id'], + values: { + id: [1, 2, 3] + } + }, + isSaved: true + } + // mock store state + const state = { + tabs: [tab1, tab2], + currentTabId: 1, + currentTab: tab1, + db: {}, + inquiries + } + + const store = createStore({ state, mutations, actions }) + const router = createRouter({ + history: createWebHistory(), + routes: routes + }) + router.push('/workspace') + + // After this line, router is ready + await router.isReady() + + const wrapper = mount(App, { + attachTo: document.body, + global: { + stubs: { + 'router-link': true, + teleport: true, + transition: false, + schema: true, + AppDiagnosticInfo: true, + DataView: { + template: '
', + methods: { getOptionsForSave: sinon.stub() } + } + }, + plugins: [store, router] + } + }) + // click on the close icon of the first tab + const firstTabCloseIcon = wrapper.findAll('.tab')[0].find('.close-icon') + await firstTabCloseIcon.trigger('click') + + // find 'Save and close' in the dialog + const closeBtn = wrapper + .findAll('.dialog-buttons-container button') + .find(button => button.text() === 'Save and close') + + // click 'Save and close' in the dialog + await closeBtn.trigger('click') + + await nextTick() + await nextTick() + + // check that tab is closed + expect(wrapper.findAllComponents({ name: 'Tab' })).to.have.lengthOf(1) + // check that the open tab didn't change + const firstTab = wrapper.findComponent({ name: 'Tab' }) + expect(firstTab.props('tab').name).to.equal('bar') + expect(firstTab.props('tab').result).to.eql({ + columns: ['id'], + values: { + id: [1, 2, 3] + } + }) + expect(firstTab.props('tab')).to.eql(tab2) + + // check that the dialog is closed + await clock.tick(100) + await nextTick() + expect(wrapper.find('.dialog.vfm .vfm__content').exists()).to.equal(false) + wrapper.unmount() + }) }) diff --git a/tests/views/MainView/MainMenu.spec.js b/tests/views/MainView/MainMenu.spec.js index c8637c3..fd71637 100644 --- a/tests/views/MainView/MainMenu.spec.js +++ b/tests/views/MainView/MainMenu.spec.js @@ -759,8 +759,7 @@ describe('MainMenu.vue', () => { createdAt: '2025-05-14T15:30:00Z' } ], - tabs: [tab], - db: {} + tabs: [tab] } const mutations = { updateTab: sinon.stub() @@ -802,15 +801,17 @@ describe('MainMenu.vue', () => { 'Inquiry saving conflict' ) + await nextTick() + await clock.tick(100) + + // check that only one dialog open + expect(wrapper.findAll('.dialog.vfm').length).to.equal(1) // find "Save as new" in the dialog and click await wrapper .findAll('.dialog-buttons-container button') .find(button => button.text() === 'Save as new') .trigger('click') - await nextTick() - await clock.tick(100) - // enter the new name await wrapper.find('.dialog-body input').setValue('foo_new') @@ -821,7 +822,6 @@ describe('MainMenu.vue', () => { .trigger('click') await nextTick() - // check that the dialog is closed await clock.tick(100) expect(wrapper.find('.dialog.vfm').exists()).to.equal(false)