From 7fe9c7babc188ec89cf538dd976ce167e742eb9f Mon Sep 17 00:00:00 2001 From: "LaptopVerdnatura\\Javi" Date: Fri, 20 Mar 2020 11:36:14 +0100 Subject: [PATCH 01/15] getWarehouse --- .../10170-NOFallas/00-zone_getWarehouse.sql | 87 +++++++++++++++++++ 1 file changed, 87 insertions(+) create mode 100644 db/changes/10170-NOFallas/00-zone_getWarehouse.sql diff --git a/db/changes/10170-NOFallas/00-zone_getWarehouse.sql b/db/changes/10170-NOFallas/00-zone_getWarehouse.sql new file mode 100644 index 000000000..a65643ff5 --- /dev/null +++ b/db/changes/10170-NOFallas/00-zone_getWarehouse.sql @@ -0,0 +1,87 @@ +USE `vn`; +DROP procedure IF EXISTS `zone_getWarehouse`; + +DELIMITER $$ +USE `vn`$$ +CREATE DEFINER=`root`@`%` PROCEDURE `zone_getWarehouse`(vAddress INT, vLanded DATE, vWarehouse INT) +BEGIN +/** + * Devuelve el listado de agencias disponibles para la fecha, + * dirección y almacén pasados. + * + * @param vAddress + * @param vWarehouse warehouse + * @param vLanded Fecha de recogida + * @select Listado de agencias disponibles + */ + + CALL zone_getFromGeo(address_getGeo(vAddress)); + CALL zone_getOptionsForLanding(vLanded, FALSE); + + SELECT am.id agencyModeFk, + am.name agencyMode, + am.description, + am.deliveryMethodFk, + TIMESTAMPADD(DAY, -zo.travelingDays, vLanded) shipped, + zw.warehouseFk, + z.id zoneFk + FROM tmp.zoneOption zo + JOIN zone z ON z.id = zo.zoneFk + JOIN agencyMode am ON am.id = z.agencyModeFk + JOIN zoneWarehouse zw ON zw.zoneFk = zo.zoneFk + WHERE zw.warehouseFk = vWarehouse + GROUP BY z.agencyModeFk + ORDER BY agencyMode; + + DROP TEMPORARY TABLE + tmp.zone, + tmp.zoneOption; + +END$$ + +DELIMITER ; + +USE `vn`; +DROP procedure IF EXISTS `zone_getWarehouse__`; + +DELIMITER $$ +USE `vn`$$ +CREATE DEFINER=`root`@`%` PROCEDURE `zone_getWarehouse__`(vAddress INT, vLanded DATE, vWarehouse INT) +BEGIN +/** + * Devuelve el listado de agencias disponibles para la fecha, + * dirección y almacén pasados. + * + * @param vAddress + * @param vWarehouse warehouse + * @param vLanded Fecha de recogida + * @select Listado de agencias disponibles + */ + + CALL zone_getFromGeo(address_getGeo(vAddress)); + CALL zone_getOptionsForLanding(vLanded, FALSE); + + SELECT am.id agencyModeFk, + am.name agencyMode, + am.description, + am.deliveryMethodFk, + TIMESTAMPADD(DAY, -zo.travelingDays, vLanded) shipped, + zw.warehouseFk, + z.id zoneFk + FROM tmp.zoneOption zo + JOIN zone z ON z.id = zo.zoneFk + JOIN agencyMode am ON am.id = z.agencyModeFk + JOIN zoneWarehouse zw ON zw.zoneFk = zo.zoneFk + WHERE zw.warehouseFk + GROUP BY z.agencyModeFk + ORDER BY agencyMode; + + DROP TEMPORARY TABLE + tmp.zone, + tmp.zoneOption; + +END$$ + +DELIMITER ; + + From 6d4e83fa990e9944b22e5fd1abe80b92db5d3409 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Fri, 20 Mar 2020 12:42:06 +0100 Subject: [PATCH 02/15] E2E fixes --- e2e/helpers/selectors.js | 2 +- e2e/paths/04-item/09_regularize.spec.js | 1 - e2e/paths/09-invoice-out/02_descriptor.spec.js | 14 ++------------ 3 files changed, 3 insertions(+), 14 deletions(-) diff --git a/e2e/helpers/selectors.js b/e2e/helpers/selectors.js index 0cee79405..2ac6f4223 100644 --- a/e2e/helpers/selectors.js +++ b/e2e/helpers/selectors.js @@ -208,7 +208,7 @@ export default { createItemButton: `vn-float-button`, firstSearchResult: 'vn-item-index a:nth-child(1)', searchResult: 'vn-item-index a.vn-tr', - searchResultPreviewButton: 'vn-item-index .buttons > [icon="desktop_windows"]', + searchResultPreviewButton: 'vn-item-index vn-tbody > :nth-child(1) .buttons > [icon="desktop_windows"]', searchResultCloneButton: 'vn-item-index .buttons > [icon="icon-clone"]', acceptClonationAlertButton: '.vn-confirm.shown [response="accept"]', topbarSearch: 'vn-topbar', diff --git a/e2e/paths/04-item/09_regularize.spec.js b/e2e/paths/04-item/09_regularize.spec.js index 838b24cf0..18f182e74 100644 --- a/e2e/paths/04-item/09_regularize.spec.js +++ b/e2e/paths/04-item/09_regularize.spec.js @@ -78,7 +78,6 @@ describe('Item regularize path', () => { }); it('should search for the ticket with alias missing', async() => { - await page.accessToSearchResult('Carol Danvers'); await page.keyboard.press('Escape'); await page.accessToSearchResult('missing'); let url = await page.expectURL('/summary'); diff --git a/e2e/paths/09-invoice-out/02_descriptor.spec.js b/e2e/paths/09-invoice-out/02_descriptor.spec.js index e70c39ded..1290b9a88 100644 --- a/e2e/paths/09-invoice-out/02_descriptor.spec.js +++ b/e2e/paths/09-invoice-out/02_descriptor.spec.js @@ -20,10 +20,9 @@ describe('InvoiceOut descriptor path', () => { await page.waitToClick(selectors.ticketsIndex.openAdvancedSearchButton); await page.write(selectors.ticketsIndex.advancedSearchInvoiceOut, 'T2222222'); await page.waitToClick(selectors.ticketsIndex.advancedSearchButton); - await page.waitForNumberOfElements(selectors.ticketsIndex.searchResult, 1); - const result = await page.countElement(selectors.ticketsIndex.searchResult); + let url = await page.expectURL('#!/ticket/3/summary'); - expect(result).toEqual(1); + expect(url).toEqual(true); }); it('should navigate to the invoiceOut index', async() => { @@ -36,15 +35,6 @@ describe('InvoiceOut descriptor path', () => { expect(url).toBe(true); }); - it('should search for the target invoiceOut', async() => { - await page.write(selectors.invoiceOutIndex.topbarSearch, 'T2222222'); - await page.waitToClick(selectors.invoiceOutIndex.searchButton); - await page.waitForNumberOfElements(selectors.invoiceOutIndex.searchResult, 1); - const result = await page.countElement(selectors.invoiceOutIndex.searchResult); - - expect(result).toEqual(1); - }); - it(`should click on the search result to access to the invoiceOut summary`, async() => { await page.accessToSearchResult('T2222222'); let url = await page.expectURL('/summary'); From 0a7ce19fb99828423092bbf925bd3a1341666460 Mon Sep 17 00:00:00 2001 From: Bernat Date: Fri, 20 Mar 2020 16:18:38 +0100 Subject: [PATCH 03/15] small fix --- e2e/helpers/selectors.js | 2 +- e2e/paths/04-item/01_summary.spec.js | 9 ++++----- 2 files changed, 5 insertions(+), 6 deletions(-) diff --git a/e2e/helpers/selectors.js b/e2e/helpers/selectors.js index 2ac6f4223..89857f770 100644 --- a/e2e/helpers/selectors.js +++ b/e2e/helpers/selectors.js @@ -208,7 +208,7 @@ export default { createItemButton: `vn-float-button`, firstSearchResult: 'vn-item-index a:nth-child(1)', searchResult: 'vn-item-index a.vn-tr', - searchResultPreviewButton: 'vn-item-index vn-tbody > :nth-child(1) .buttons > [icon="desktop_windows"]', + firstResultPreviewButton: 'vn-item-index vn-tbody > :nth-child(1) .buttons > [icon="desktop_windows"]', searchResultCloneButton: 'vn-item-index .buttons > [icon="icon-clone"]', acceptClonationAlertButton: '.vn-confirm.shown [response="accept"]', topbarSearch: 'vn-topbar', diff --git a/e2e/paths/04-item/01_summary.spec.js b/e2e/paths/04-item/01_summary.spec.js index 01e730668..6fd4e9c13 100644 --- a/e2e/paths/04-item/01_summary.spec.js +++ b/e2e/paths/04-item/01_summary.spec.js @@ -19,8 +19,8 @@ describe('Item summary path', () => { await page.write(selectors.itemsIndex.topbarSearch, 'Ranged weapon'); await page.waitToClick(selectors.itemsIndex.searchButton); await page.waitForNumberOfElements(selectors.itemsIndex.searchResult, 3); - await page.waitForTextInElement(selectors.itemsIndex.searchResult, 'Ranged weapon longbow 2m'); - await page.waitToClick(selectors.itemsIndex.searchResultPreviewButton); + await page.waitForTextInElement(selectors.itemsIndex.searchResult, 'Ranged weapon'); + await page.waitToClick(selectors.itemsIndex.firstResultPreviewButton); const isVisible = await page.isVisible(selectors.itemSummary.basicData); expect(isVisible).toBeTruthy(); @@ -68,11 +68,10 @@ describe('Item summary path', () => { it('should search for other item', async() => { await page.clearInput('vn-searchbar'); - await page.waitToClick(selectors.itemsIndex.searchButton); await page.write(selectors.itemsIndex.topbarSearch, 'Melee Reinforced'); - await page.waitToClick(selectors.itemsIndex.searchButton); + await page.keyboard.press('Enter'); await page.waitForNumberOfElements(selectors.itemsIndex.searchResult, 2); - await page.waitToClick(selectors.itemsIndex.searchResultPreviewButton); + await page.waitToClick(selectors.itemsIndex.firstResultPreviewButton); await page.waitForSelector(selectors.itemSummary.basicData, {visible: true}); }); From 6dcee3516d357f80bfa82230e9e6faa3def46bd6 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Mon, 23 Mar 2020 10:40:09 +0100 Subject: [PATCH 04/15] ticket e2e fixes --- e2e/helpers/selectors.js | 2 +- e2e/paths/05-ticket/09_weekly.spec.js | 11 +---------- e2e/paths/05-ticket/12_descriptor.spec.js | 3 +-- front/core/components/searchbar/searchbar.js | 2 ++ 4 files changed, 5 insertions(+), 13 deletions(-) diff --git a/e2e/helpers/selectors.js b/e2e/helpers/selectors.js index 89857f770..88f7cb40d 100644 --- a/e2e/helpers/selectors.js +++ b/e2e/helpers/selectors.js @@ -369,7 +369,7 @@ export default { newTicketButton: 'vn-ticket-index a', searchResult: 'vn-ticket-index vn-card > vn-table > div > vn-tbody > a.vn-tr', searchWeeklyResult: 'vn-ticket-weekly-index vn-table vn-tbody > vn-tr', - searchResultDate: 'vn-ticket-index vn-table vn-tbody > a:nth-child(1) > vn-td:nth-child(5)', + searchResultDate: 'vn-ticket-summary [label=Landed] span', topbarSearch: 'vn-searchbar', advancedSearchButton: 'vn-ticket-search-panel button[type=submit]', searchButton: 'vn-searchbar vn-icon[icon="search"]', diff --git a/e2e/paths/05-ticket/09_weekly.spec.js b/e2e/paths/05-ticket/09_weekly.spec.js index 3e791dc18..9213afd1d 100644 --- a/e2e/paths/05-ticket/09_weekly.spec.js +++ b/e2e/paths/05-ticket/09_weekly.spec.js @@ -63,16 +63,7 @@ describe('Ticket descriptor path', () => { }); it('should now search for the ticket 11', async() => { - await page.write(selectors.ticketsIndex.topbarSearch, '11'); - await page.waitToClick(selectors.ticketsIndex.searchButton); - await page.waitForNumberOfElements(selectors.ticketsIndex.searchResult, 1); - const result = await page.countElement(selectors.ticketsIndex.searchResult); - - expect(result).toEqual(1); - }); - - it(`should click on the search result to access to the ticket`, async() => { - await page.waitToClick(selectors.ticketsIndex.searchResult); + await page.accessToSearchResult('11'); let url = await page.expectURL('/summary'); expect(url).toBe(true); diff --git a/e2e/paths/05-ticket/12_descriptor.spec.js b/e2e/paths/05-ticket/12_descriptor.spec.js index 59691d380..0e3712c82 100644 --- a/e2e/paths/05-ticket/12_descriptor.spec.js +++ b/e2e/paths/05-ticket/12_descriptor.spec.js @@ -58,8 +58,7 @@ describe('Ticket descriptor path', () => { it(`should search for the deleted ticket and check it's date`, async() => { await page.write(selectors.ticketsIndex.topbarSearch, '18'); await page.waitToClick(selectors.ticketsIndex.searchButton); - await page.waitForNumberOfElements(selectors.ticketsIndex.searchResult, 1); - await page.wait(selectors.ticketsIndex.searchResultDate); + await page.expectURL('/summary'); const result = await page.waitToGetProperty(selectors.ticketsIndex.searchResultDate, 'innerText'); expect(result).toContain(2000); diff --git a/front/core/components/searchbar/searchbar.js b/front/core/components/searchbar/searchbar.js index 640ed48d6..21e72f60d 100644 --- a/front/core/components/searchbar/searchbar.js +++ b/front/core/components/searchbar/searchbar.js @@ -239,6 +239,8 @@ export default class Searchbar extends Component { this.filter = filter; + if (!filter && this.model) + this.model.clear(); if (source != 'state') this.transition = this.$state.go(state, params, opts).transition; if (source != 'bar') From 84bf240e71dfc4e00dad308cb20cb3a9d057e5a2 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Mon, 23 Mar 2020 23:57:11 +0100 Subject: [PATCH 05/15] All tests passed, but some intermittence in e2e --- db/dump/fixtures.sql | 38 +- e2e/helpers/extensions.js | 330 +++++++++--------- e2e/helpers/puppeteer.js | 7 +- e2e/paths/01-login/01_login.spec.js | 56 +-- e2e/paths/02-client/01_create_client.spec.js | 5 +- .../12_lock_of_verified_data.spec.js | 2 +- .../05-ticket/02_expeditions_and_log.spec.js | 3 +- e2e/paths/05-ticket/13_services.spec.js | 3 - e2e/paths/05-ticket/14_create_ticket.spec.js | 5 +- e2e/paths/06-claim/01_basic_data.spec.js | 4 +- e2e/paths/06-claim/04_claim_action.spec.js | 2 +- e2e/paths/07-order/02_basic_data.spec.js | 3 +- e2e/paths/07-order/04_catalog.spec.js | 4 +- e2e/paths/08-route/02_basic_data.spec.js | 6 +- e2e/paths/08-route/03_create.spec.js | 2 +- .../10-travel/02_basic_data_and_log.spec.js | 5 +- e2e/paths/11-zone/01_basic-data.spec.js | 9 +- front/core/components/snackbar/snackbar.js | 133 ++++--- package-lock.json | 45 +-- 19 files changed, 338 insertions(+), 324 deletions(-) diff --git a/db/dump/fixtures.sql b/db/dump/fixtures.sql index 7b2fd1cae..331d115a3 100644 --- a/db/dump/fixtures.sql +++ b/db/dump/fixtures.sql @@ -471,19 +471,19 @@ INSERT INTO `vn`.`invoiceOutSerial` (`code`, `description`, `isTaxed`, `taxAreaF INSERT INTO `vn`.`zone` (`id`, `name`, `hour`, `agencyModeFk`, `travelingDays`, `price`, `bonus`, `m3Max`) VALUES - (1, 'Zone pickup A', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 1, 0, 0, 0, 30.50), - (2, 'Zone pickup B', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 1, 0, 0, 0, 30.50), - (3, 'Zone 247 A', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 7, 1, 2, 0, 40.50), - (4, 'Zone 247 B', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 7, 1, 2, 0, 40.50), - (5, 'Zone expensive A', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 8, 1, 1000, 0, 50.50), - (6, 'Zone expensive B', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 8, 1, 1000, 0, 50.50), - (7, 'Zone refund', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 23, 0, 0, 0, 60.50), - (8, 'Zone others', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 10, 0, 0, 0, 60.50), - (9, 'Zone superMan', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 2, 0, 0, 0, NULL), - (10, 'Zone teleportation', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 3, 0, 0, 0, NULL), - (11, 'Zone pickup C', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 1, 0, 0, 0, NULL), - (12, 'Zone entanglement', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 4, 0, 0, 0, NULL), - (13, 'Zone quantum break', CONCAT(CURRENT_DATE(), ' ', TIME('22:00')), 5, 0, 0, 0, NULL); + (1, 'Zone pickup A', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 1, 0, 0, 0, 30.50), + (2, 'Zone pickup B', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 1, 0, 0, 0, 30.50), + (3, 'Zone 247 A', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 7, 1, 2, 0, 40.50), + (4, 'Zone 247 B', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 7, 1, 2, 0, 40.50), + (5, 'Zone expensive A', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 8, 1, 1000, 0, 50.50), + (6, 'Zone expensive B', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 8, 1, 1000, 0, 50.50), + (7, 'Zone refund', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 23, 0, 0, 0, 60.50), + (8, 'Zone others', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 10, 0, 0, 0, 60.50), + (9, 'Zone superMan', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 2, 0, 0, 0, NULL), + (10, 'Zone teleportation', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 3, 0, 0, 0, NULL), + (11, 'Zone pickup C', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 1, 0, 0, 0, NULL), + (12, 'Zone entanglement', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 4, 0, 0, 0, NULL), + (13, 'Zone quantum break', CONCAT(CURRENT_DATE(), ' ', TIME('23:59')), 5, 0, 0, 0, NULL); INSERT INTO `vn`.`zoneWarehouse` (`id`, `zoneFk`, `warehouseFk`) VALUES @@ -1890,14 +1890,10 @@ INSERT INTO `vn`.`zoneEvent`(`zoneFk`, `type`, `dated`) (7, 'day', DATE_ADD(CURDATE(), INTERVAL +3 DAY)), (7, 'day', DATE_ADD(CURDATE(), INTERVAL +4 DAY)), (7, 'day', DATE_ADD(CURDATE(), INTERVAL +5 DAY)), - (7, 'day', DATE_ADD(CURDATE(), INTERVAL +6 DAY)), - (8, 'day', CURDATE()), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +1 DAY)), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +2 DAY)), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +3 DAY)), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +4 DAY)), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +5 DAY)), - (8, 'day', DATE_ADD(CURDATE(), INTERVAL +6 DAY)); + (7, 'day', DATE_ADD(CURDATE(), INTERVAL +6 DAY)); + +INSERT INTO `vn`.`zoneEvent`(`zoneFk`, `type`, `weekDays`) + VALUES (8, 'indefinitely', 'mon,tue,wed,thu,fri,sat,sun'); INSERT INTO `vn`.`workerTimeControl`(`userFk`, `timed`, `manual`, `direction`) VALUES diff --git a/e2e/helpers/extensions.js b/e2e/helpers/extensions.js index 5fe362043..cccf85391 100644 --- a/e2e/helpers/extensions.js +++ b/e2e/helpers/extensions.js @@ -1,45 +1,3 @@ -import {url as defaultURL} from './config'; - -function checkVisibility(selector) { - let selectorMatches = document.querySelectorAll(selector); - let element = selectorMatches[0]; - - if (selectorMatches.length > 1) - throw new Error(`Multiple matches of ${selector} found`); - - let isVisible = false; - if (element) { - let eventHandler = event => { - event.preventDefault(); - isVisible = true; - }; - element.addEventListener('mouseover', eventHandler); - let rect = element.getBoundingClientRect(); - let x = rect.left + rect.width / 2; - let y = rect.top + rect.height / 2; - let elementInCenter = document.elementFromPoint(x, y); - let elementInTopLeft = document.elementFromPoint(rect.left, rect.top); - let elementInBottomRight = document.elementFromPoint(rect.right, rect.bottom); - - let e = new MouseEvent('mouseover', { - view: window, - bubbles: true, - cancelable: true, - }); - - if (elementInCenter) - elementInCenter.dispatchEvent(e); - - if (elementInTopLeft) - elementInTopLeft.dispatchEvent(e); - - if (elementInBottomRight) - elementInBottomRight.dispatchEvent(e); - - element.removeEventListener('mouseover', eventHandler); - } - return isVisible; -} let actions = { clickIfExists: async function(selector) { @@ -65,12 +23,6 @@ let actions = { return true; }, - waitUntilNotPresent: async function(selector) { - await this.wait(selector => { - return document.querySelector(selector) == null; - }, selector); - }, - doLogin: async function(userName, password = 'nightmare') { await this.waitForSelector(`vn-login vn-textfield[ng-model="$ctrl.user"]`, {visible: true}); await this.clearInput(`vn-login vn-textfield[ng-model="$ctrl.user"]`); @@ -81,27 +33,31 @@ let actions = { }, login: async function(userName) { - await this.goto(`${defaultURL}/#!/login`); - let dialog = await this.evaluate(() => { - return document.querySelector('button[response="accept"]'); - }); - if (dialog) - await this.waitToClick('button[response="accept"]'); + let state = await this.getState(); + if (state != 'login') { + try { + await this.gotoState('login'); + } catch (err) { + let dialog = await this.evaluate( + () => document.querySelector('button[response="accept"]')); + + if (dialog) + await this.waitToClick('button[response="accept"]'); + else + throw err; + } + } + + await this.waitForState('login'); await this.doLogin(userName); - await this.waitForFunction(() => { - return document.location.hash === '#!/'; - }, {}); + await this.waitForState('home'); }, selectModule: async function(moduleName) { - let snakeName = moduleName.replace(/[\w]([A-Z])/g, m => { - return m[0] + '-' + m[1]; - }).toLowerCase(); - - let selector = `vn-home a[ui-sref="${moduleName}.index"]`; - await this.waitToClick(selector); - await this.expectURL(snakeName); + let state = `${moduleName}.index`; + await this.waitToClick(`vn-home a[ui-sref="${state}"]`); + await this.waitForState(state); }, loginAndModule: async function(userName, moduleName) { @@ -109,56 +65,73 @@ let actions = { await this.selectModule(moduleName); }, - datePicker: async function(selector, changeMonth, day) { - let date = new Date(); - if (changeMonth) date.setMonth(date.getMonth() + changeMonth); - date.setDate(day ? day : 16); - date = date.toISOString().substr(0, 10); - - await this.wait(selector); - await this.evaluate((selector, date) => { - let input = document.querySelector(selector).$ctrl.input; - input.value = date; - input.dispatchEvent(new Event('change')); - }, selector, date); + getState: async function() { + return await this.evaluate(() => { + let $state = angular.element(document.body).injector().get('$state'); + return $state.current.name; + }); }, - pickTime: async function(selector, time) { - await this.wait(selector); - await this.evaluate((selector, time) => { - let input = document.querySelector(selector).$ctrl.input; - input.value = time; - input.dispatchEvent(new Event('change')); - }, selector, time); + gotoState: async function(state, params) { + return await this.evaluate((state, params) => { + let $state = angular.element(document.body).injector().get('$state'); + return $state.go(state, params); + }, state, params); }, - clearTextarea: async function(selector) { - await this.waitForSelector(selector, {visible: true}); - await this.evaluate(inputSelector => { - return document.querySelector(`${inputSelector} textarea`).value = ''; - }, selector); + waitForState: async function(state) { + await this.waitFor(state => { + let $state = angular.element(document.body).injector().get('$state'); + return $state.is(state); + }, {}, state); }, - clearInput: async function(selector) { - await this.waitForSelector(selector); + waitForTransition: async function() { + await this.waitFor(() => { + const $state = angular.element(document.body).injector().get('$state'); + return !$state.transition; + }); + }, - let field = await this.evaluate(selector => { - return document.querySelector(`${selector} input`).closest('.vn-field').$ctrl.field; - }, selector); + accessToSection: async function(state) { + await this.waitForSelector('vn-left-menu'); + let nested = await this.evaluate(state => { + return document.querySelector(`vn-left-menu li li > a[ui-sref="${state}"]`) != null; + }, state); - if ((field != null && field != '') || field == '0') { - let coords = await this.evaluate(selector => { - let rect = document.querySelector(selector).getBoundingClientRect(); - return {x: rect.x + (rect.width / 2), y: rect.y + (rect.height / 2), width: rect.width}; - }, selector); - await this.mouse.move(coords.x, coords.y); - await this.waitForSelector(`${selector} [icon="clear"]`, {visible: true}); - await this.waitToClick(`${selector} [icon="clear"]`); + if (nested) { + await this.waitToClick('vn-left-menu vn-item-section > vn-icon[icon=keyboard_arrow_down]'); + await this.wait('vn-left-menu .expanded'); } - await this.evaluate(selector => { - return document.querySelector(`${selector} input`).closest('.vn-field').$ctrl.field == ''; - }, selector); + await this.evaluate(state => { + let navButton = document.querySelector(`vn-left-menu li > a[ui-sref="${state}"]`); + navButton.scrollIntoViewIfNeeded(); + return navButton.click(); + }, state); + + await this.waitForState(state); + await this.waitForContentLoaded(); + }, + + reloadSection: async function(state) { + await this.click('vn-icon[icon="desktop_windows"]'); + await this.accessToSection(state); + }, + + forceReloadSection: async function(sectionRoute) { + await this.waitToClick('vn-icon[icon="desktop_windows"]'); + await this.waitToClick('button[response="accept"]'); + await this.wait('vn-card.summary'); + await this.waitToClick(`vn-left-menu li > a[ui-sref="${sectionRoute}"]`); + }, + + accessToSearchResult: async function(searchValue) { + await this.clearInput('vn-searchbar'); + await this.write('vn-searchbar', searchValue); + await this.waitToClick('vn-searchbar vn-icon[icon="search"]'); + await this.waitForTransition(); + await this.waitForContentLoaded(); }, getProperty: async function(selector, property) { @@ -216,7 +189,7 @@ let actions = { waitToClick: async function(selector) { await this.waitForSelector(selector); - await this.waitForFunction(checkVisibility, {}, selector); + await this.checkVisibility(selector); return await this.click(selector); }, @@ -236,9 +209,52 @@ let actions = { }, selector); }, + checkVisibility: async function(selector) { + return await this.evaluate(function(selector) { + let selectorMatches = document.querySelectorAll(selector); + let element = selectorMatches[0]; + + if (selectorMatches.length > 1) + throw new Error(`Multiple matches of ${selector} found`); + + let isVisible = false; + if (element) { + let eventHandler = event => { + event.preventDefault(); + isVisible = true; + }; + element.addEventListener('mouseover', eventHandler); + let rect = element.getBoundingClientRect(); + let x = rect.left + rect.width / 2; + let y = rect.top + rect.height / 2; + let elementInCenter = document.elementFromPoint(x, y); + let elementInTopLeft = document.elementFromPoint(rect.left, rect.top); + let elementInBottomRight = document.elementFromPoint(rect.right, rect.bottom); + + let e = new MouseEvent('mouseover', { + view: window, + bubbles: true, + cancelable: true, + }); + + if (elementInCenter) + elementInCenter.dispatchEvent(e); + + if (elementInTopLeft) + elementInTopLeft.dispatchEvent(e); + + if (elementInBottomRight) + elementInBottomRight.dispatchEvent(e); + + element.removeEventListener('mouseover', eventHandler); + } + return isVisible; + }, selector); + }, + isVisible: async function(selector) { await this.waitForSelector(selector); - return await this.evaluate(checkVisibility, selector); + return await this.checkVisibility(selector); }, waitImgLoad: async function(selector) { @@ -320,12 +336,13 @@ let actions = { }, hideSnackbar: async function() { - await this.waitFor(750); // holds up for the snackbar to be visible for a small period of time. + await this.waitFor(300); // holds up for the snackbar to be visible for a small period of time. await this.evaluate(() => { let hideButton = document.querySelector('#shapes .shown button'); if (hideButton) return document.querySelector('#shapes .shown button').click(); }); + await this.waitFor('#shapes > .shape', {hidden: true}); }, waitForLastSnackbar: async function() { @@ -341,37 +358,59 @@ let actions = { return snackBarText; }, - accessToSearchResult: async function(searchValue) { - await this.clearInput('vn-searchbar'); - await this.write('vn-searchbar', searchValue); - await this.waitToClick('vn-searchbar vn-icon[icon="search"]'); - await this.waitForContentLoaded(); + pickDate: async function(selector, date) { + date = date || new Date(); + date = date.toISOString().substr(0, 10); + + await this.wait(selector); + await this.evaluate((selector, date) => { + let input = document.querySelector(selector).$ctrl.input; + input.value = date; + input.dispatchEvent(new Event('change')); + }, selector, date); }, - accessToSection: async function(sectionRoute) { - await this.waitForSelector('vn-left-menu'); - let nested = await this.evaluate(sectionRoute => { - return document.querySelector(`vn-left-menu li li > a[ui-sref="${sectionRoute}"]`) != null; - }, sectionRoute); + pickTime: async function(selector, time) { + await this.wait(selector); + await this.evaluate((selector, time) => { + let input = document.querySelector(selector).$ctrl.input; + input.value = time; + input.dispatchEvent(new Event('change')); + }, selector, time); + }, - if (nested) { - await this.waitToClick('vn-left-menu vn-item-section > vn-icon[icon=keyboard_arrow_down]'); - await this.wait('vn-left-menu .expanded'); + clearTextarea: async function(selector) { + await this.waitForSelector(selector, {visible: true}); + await this.evaluate(inputSelector => { + return document.querySelector(`${inputSelector} textarea`).value = ''; + }, selector); + }, + + clearInput: async function(selector) { + await this.waitForSelector(selector); + + let field = await this.evaluate(selector => { + return document.querySelector(`${selector} input`).closest('.vn-field').$ctrl.field; + }, selector); + + if ((field != null && field != '') || field == '0') { + let coords = await this.evaluate(selector => { + let rect = document.querySelector(selector).getBoundingClientRect(); + return {x: rect.x + (rect.width / 2), y: rect.y + (rect.height / 2), width: rect.width}; + }, selector); + await this.mouse.move(coords.x, coords.y); + await this.waitForSelector(`${selector} [icon="clear"]`, {visible: true}); + await this.waitToClick(`${selector} [icon="clear"]`); } - await this.evaluate(sectionRoute => { - let navButton = document.querySelector(`vn-left-menu li > a[ui-sref="${sectionRoute}"]`); - navButton.scrollIntoViewIfNeeded(); - return navButton.click(); - }, sectionRoute); - await this.waitForNavigation({waitUntil: ['networkidle0']}); - await this.waitForContentLoaded(); + await this.evaluate(selector => { + return document.querySelector(`${selector} input`).closest('.vn-field').$ctrl.field == ''; + }, selector); }, autocompleteSearch: async function(selector, searchValue) { let builtSelector = await this.selectorFormater(selector); - await this.waitForContentLoaded(); await this.waitToClick(selector); await this.waitForSelector(selector => { document @@ -402,28 +441,7 @@ let actions = { }, {}, builtSelector, searchValue); await this.waitForMutation('.vn-drop-down', 'childList'); - await this.waitForContentLoaded(); - }, - - reloadSection: async function(sectionRoute) { - await this.waitForContentLoaded(); - await Promise.all([ - this.waitForNavigation({waitUntil: 'networkidle0'}), - this.click('vn-icon[icon="desktop_windows"]', {}), - ]); - - await Promise.all([ - this.waitForNavigation({waitUntil: 'networkidle0'}), - this.click(`vn-left-menu li > a[ui-sref="${sectionRoute}"]`, {}), - ]); - await this.waitForContentLoaded(); - }, - - forceReloadSection: async function(sectionRoute) { - await this.waitToClick('vn-icon[icon="desktop_windows"]'); - await this.waitToClick('button[response="accept"]'); - await this.wait('vn-card.summary'); - await this.waitToClick(`vn-left-menu li > a[ui-sref="${sectionRoute}"]`); + await this.waitFor('.vn-drop-down', {hidden: true}); }, checkboxState: async function(selector) { @@ -457,7 +475,7 @@ let actions = { }, waitForSpinnerLoad: async function() { - await this.waitUntilNotPresent('vn-topbar vn-spinner'); + await this.waitFor('vn-topbar vn-spinner', {hidden: true}); }, waitForWatcherData: async function(selector) { @@ -509,14 +527,10 @@ let actions = { closePopup: async function(selector) { await Promise.all([ this.keyboard.press('Escape'), - this.waitForSelector('.vn-popup', {hidden: true}), + this.waitFor('.vn-popup', {hidden: true}), ]); }, - waitForContentLoaded: async function() { - await this.waitFor(1000); - }, - respondToDialog: async function(response) { await this.waitForSelector('.vn-dialog.vn-popup.shown'); const firstCount = await this.evaluate(text => { @@ -531,6 +545,10 @@ let actions = { const dialogs = document.querySelectorAll('.vn-dialog.vn-popup'); return dialogs.length < firstCount; }, {}, firstCount); + }, + + waitForContentLoaded: async function() { + await this.waitFor(250); } }; diff --git a/e2e/helpers/puppeteer.js b/e2e/helpers/puppeteer.js index 1ca0726c0..8aa3f72f8 100644 --- a/e2e/helpers/puppeteer.js +++ b/e2e/helpers/puppeteer.js @@ -8,7 +8,8 @@ export async function getBrowser() { const browser = await Puppeteer.launch({ args: [ '--no-sandbox', - `--window-size=${ 1920 },${ 1080 }` + `--window-size=${ 1920 },${ 1080 }`, + // '--auto-open-devtools-for-tabs' ], defaultViewport: null, headless: headless, @@ -28,8 +29,8 @@ export async function getBrowser() { }); }); page = extendPage(page); - page.setDefaultTimeout(10000); - await page.goto(defaultURL, {waitUntil: 'networkidle0'}); + page.setDefaultTimeout(4000); + await page.goto(defaultURL, {waitUntil: 'load'}); return {page, close: browser.close.bind(browser)}; } diff --git a/e2e/paths/01-login/01_login.spec.js b/e2e/paths/01-login/01_login.spec.js index abb022011..6b101b00b 100644 --- a/e2e/paths/01-login/01_login.spec.js +++ b/e2e/paths/01-login/01_login.spec.js @@ -12,32 +12,42 @@ describe('Login path', async() => { await browser.close(); }); - it('should receive an error when the username is incorrect', async() => { - await page.doLogin('badUser', ''); - const result = await page.waitForLastSnackbar(); + describe('Bad login', async() => { + it('should receive an error when the username is incorrect', async() => { + await page.doLogin('badUser', ''); + const result = await page.waitForLastSnackbar(); + const state = await page.getState(); - expect(result.length).toBeGreaterThan(0); + expect(result.length).toBeGreaterThan(0); + expect(state).toBe('login'); + }); + + it('should receive an error when the username is blank', async() => { + await page.doLogin('', ''); + const result = await page.waitForLastSnackbar(); + const state = await page.getState(); + + expect(result.length).toBeGreaterThan(0); + expect(state).toBe('login'); + }); + + it('should receive an error when the password is incorrect', async() => { + await page.doLogin('employee', 'badPassword'); + const result = await page.waitForLastSnackbar(); + const state = await page.getState(); + + expect(result.length).toBeGreaterThan(0); + expect(state).toBe('login'); + }); }); - it('should receive an error when the username is blank', async() => { - await page.doLogin('', ''); - const result = await page.waitForLastSnackbar(); + describe('Successful login', async() => { + it('should log in', async() => { + await page.doLogin('employee', 'nightmare'); + await page.waitForNavigation(); + const state = await page.getState(); - expect(result.length).toBeGreaterThan(0); - }); - - it('should receive an error when the password is incorrect', async() => { - await page.doLogin('employee', 'badPassword'); - const result = await page.waitForLastSnackbar(); - - expect(result.length).toBeGreaterThan(0); - }); - - it('should log in', async() => { - await page.doLogin('employee', 'nightmare'); - await page.waitForNavigation(); - let url = await page.expectURL('#!/'); - - expect(url).toBe(true); + expect(state).toBe('home'); + }); }); }); diff --git a/e2e/paths/02-client/01_create_client.spec.js b/e2e/paths/02-client/01_create_client.spec.js index 65db9e7c6..2de38d421 100644 --- a/e2e/paths/02-client/01_create_client.spec.js +++ b/e2e/paths/02-client/01_create_client.spec.js @@ -25,10 +25,7 @@ describe('Client create path', async() => { it('should now access to the create client view by clicking the create-client floating button', async() => { await page.waitToClick(selectors.clientsIndex.createClientButton); - await page.wait(selectors.createClientView.createButton); - let url = await page.expectURL('#!/client/create'); - - expect(url).toBe(true); + await page.waitForState('client.create'); }); it('should receive an error when clicking the create button having all the form fields empty', async() => { diff --git a/e2e/paths/02-client/12_lock_of_verified_data.spec.js b/e2e/paths/02-client/12_lock_of_verified_data.spec.js index 870ce7cb1..c8e590c34 100644 --- a/e2e/paths/02-client/12_lock_of_verified_data.spec.js +++ b/e2e/paths/02-client/12_lock_of_verified_data.spec.js @@ -109,7 +109,7 @@ describe('Client lock verified data path', () => { await page.waitToClick(selectors.clientFiscalData.saveButton); const result = await page.waitForLastSnackbar(); - expect(result).toEqual(jasmine.arrayContaining([`You can't make changes on a client with verified data`])); + expect(result).toEqual(`You can't make changes on a client with verified data`); }); }); diff --git a/e2e/paths/05-ticket/02_expeditions_and_log.spec.js b/e2e/paths/05-ticket/02_expeditions_and_log.spec.js index 94fad9b69..f0accedaf 100644 --- a/e2e/paths/05-ticket/02_expeditions_and_log.spec.js +++ b/e2e/paths/05-ticket/02_expeditions_and_log.spec.js @@ -19,8 +19,9 @@ describe('Ticket expeditions and log path', () => { it(`should delete a former expedition and confirm the remaining expedition are the expected ones`, async() => { await page.waitToClick(selectors.ticketExpedition.secondExpeditionRemoveButton); - await page.waitToClick(selectors.ticketExpedition.acceptDeleteRowButton), + await page.waitToClick(selectors.ticketExpedition.acceptDeleteRowButton); await page.reloadSection('ticket.card.expedition'); + await page.waitForSelector(selectors.ticketExpedition.expeditionRow, {}); const result = await page .countElement(selectors.ticketExpedition.expeditionRow); diff --git a/e2e/paths/05-ticket/13_services.spec.js b/e2e/paths/05-ticket/13_services.spec.js index 07a0a5768..1a32ea944 100644 --- a/e2e/paths/05-ticket/13_services.spec.js +++ b/e2e/paths/05-ticket/13_services.spec.js @@ -44,9 +44,6 @@ describe('Ticket services path', () => { await page.loginAndModule('administrative', 'ticket'); await page.accessToSearchResult(editableTicketId); await page.accessToSection('ticket.card.service'); - let url = await page.expectURL('/service'); - - expect(url).toBe(true); }); it('should click on the add button to prepare the form to create a new service', async() => { diff --git a/e2e/paths/05-ticket/14_create_ticket.spec.js b/e2e/paths/05-ticket/14_create_ticket.spec.js index e501ea0ef..c44125120 100644 --- a/e2e/paths/05-ticket/14_create_ticket.spec.js +++ b/e2e/paths/05-ticket/14_create_ticket.spec.js @@ -23,9 +23,12 @@ describe('Ticket create path', () => { }); it('should succeed to create a ticket', async() => { + const nextMonth = new Date(); + nextMonth.setMonth(nextMonth.getMonth() + 1); + await page.autocompleteSearch(selectors.createTicketView.client, 'Tony Stark'); await page.autocompleteSearch(selectors.createTicketView.address, 'Tony Stark'); - await page.datePicker(selectors.createTicketView.deliveryDate, 1, null); + await page.pickDate(selectors.createTicketView.deliveryDate, nextMonth); await page.autocompleteSearch(selectors.createTicketView.warehouse, 'Warehouse One'); await page.autocompleteSearch(selectors.createTicketView.agency, 'Silla247'); await page.waitToClick(selectors.createTicketView.createButton); diff --git a/e2e/paths/06-claim/01_basic_data.spec.js b/e2e/paths/06-claim/01_basic_data.spec.js index 9718fb583..2eb35b078 100644 --- a/e2e/paths/06-claim/01_basic_data.spec.js +++ b/e2e/paths/06-claim/01_basic_data.spec.js @@ -27,7 +27,7 @@ describe('Claim edit basic data path', () => { await page.waitToClick(selectors.claimBasicData.saveButton); const result = await page.waitForLastSnackbar(); - expect(result).toEqual(jasmine.arrayContaining(['Data saved!'])); + expect(result).toEqual('Data saved!'); }); it(`should have been redirected to the next section of claims as the role is salesAssistant`, async() => { @@ -58,6 +58,6 @@ describe('Claim edit basic data path', () => { await page.waitToClick(selectors.claimBasicData.saveButton); const result = await page.waitForLastSnackbar(); - expect(result).toEqual(jasmine.arrayContaining(['Data saved!'])); + expect(result).toEqual('Data saved!'); }); }); diff --git a/e2e/paths/06-claim/04_claim_action.spec.js b/e2e/paths/06-claim/04_claim_action.spec.js index 1db3938d5..a482e21c3 100644 --- a/e2e/paths/06-claim/04_claim_action.spec.js +++ b/e2e/paths/06-claim/04_claim_action.spec.js @@ -67,7 +67,7 @@ describe('Claim action path', () => { await page.waitToClick(selectors.claimAction.isPaidWithManaCheckbox); const result = await page.waitForLastSnackbar(); - expect(result).toEqual(jasmine.arrayContaining(['Data saved!'])); + expect(result).toEqual('Data saved!'); }); it('should confirm the "is paid with mana" checkbox is checked', async() => { diff --git a/e2e/paths/07-order/02_basic_data.spec.js b/e2e/paths/07-order/02_basic_data.spec.js index 768985628..733ccaa1a 100644 --- a/e2e/paths/07-order/02_basic_data.spec.js +++ b/e2e/paths/07-order/02_basic_data.spec.js @@ -4,7 +4,6 @@ import getBrowser from '../../helpers/puppeteer'; describe('Order edit basic data path', () => { let browser; let page; - const today = new Date().getDate(); beforeAll(async() => { browser = await getBrowser(); @@ -67,7 +66,7 @@ describe('Order edit basic data path', () => { it('should now create a new one', async() => { await page.autocompleteSearch(selectors.createOrderView.client, 'Jessica Jones'); - await page.datePicker(selectors.createOrderView.landedDatePicker, 0, today); + await page.pickDate(selectors.createOrderView.landedDatePicker); await page.autocompleteSearch(selectors.createOrderView.agency, 'Other agency'); await page.waitToClick(selectors.createOrderView.createButton); let url = await page.expectURL('/catalog'); diff --git a/e2e/paths/07-order/04_catalog.spec.js b/e2e/paths/07-order/04_catalog.spec.js index ca6489779..8c3106f6c 100644 --- a/e2e/paths/07-order/04_catalog.spec.js +++ b/e2e/paths/07-order/04_catalog.spec.js @@ -23,10 +23,8 @@ describe('Order catalog', () => { }); it('should create a new order', async() => { - let today = new Date().getDate(); - await page.autocompleteSearch(selectors.createOrderView.client, 'Tony Stark'); - await page.datePicker(selectors.createOrderView.landedDatePicker, 0, today); + await page.pickDate(selectors.createOrderView.landedDatePicker); await page.autocompleteSearch(selectors.createOrderView.agency, 'Other agency'); await page.waitToClick(selectors.createOrderView.createButton); let url = await page.expectURL('/catalog'); diff --git a/e2e/paths/08-route/02_basic_data.spec.js b/e2e/paths/08-route/02_basic_data.spec.js index 91688b3ff..66e516366 100644 --- a/e2e/paths/08-route/02_basic_data.spec.js +++ b/e2e/paths/08-route/02_basic_data.spec.js @@ -18,9 +18,12 @@ describe('Route basic Data path', () => { }); it('should edit the route basic data', async() => { + const nextMonth = new Date(); + nextMonth.setMonth(nextMonth.getMonth() + 1); + await page.autocompleteSearch(selectors.routeBasicData.worker, 'adminBossNick'); await page.autocompleteSearch(selectors.routeBasicData.vehicle, '1111-IMK'); - await page.datePicker(selectors.routeBasicData.createdDate, 1, null); + await page.pickDate(selectors.routeBasicData.createdDate, nextMonth); await page.clearInput(selectors.routeBasicData.kmStart); await page.write(selectors.routeBasicData.kmStart, '1'); await page.clearInput(selectors.routeBasicData.kmEnd); @@ -37,7 +40,6 @@ describe('Route basic Data path', () => { await page.reloadSection('route.card.basicData'); const worker = await page.waitToGetProperty(selectors.routeBasicData.worker, 'value'); - expect(worker).toEqual('adminBoss - adminBossNick'); }); diff --git a/e2e/paths/08-route/03_create.spec.js b/e2e/paths/08-route/03_create.spec.js index 11ffd500b..c929e647f 100644 --- a/e2e/paths/08-route/03_create.spec.js +++ b/e2e/paths/08-route/03_create.spec.js @@ -48,7 +48,7 @@ describe('Route create path', () => { it(`should create a new route`, async() => { await page.autocompleteSearch(selectors.createRouteView.worker, 'teamManagerNick'); - await page.datePicker(selectors.createRouteView.createdDatePicker, 0, null); + await page.pickDate(selectors.createRouteView.createdDatePicker); await page.autocompleteSearch(selectors.createRouteView.vehicleAuto, '4444-IMK'); await page.autocompleteSearch(selectors.createRouteView.agency, 'Teleportation device'); await page.write(selectors.createRouteView.description, 'faster faster!!'); diff --git a/e2e/paths/10-travel/02_basic_data_and_log.spec.js b/e2e/paths/10-travel/02_basic_data_and_log.spec.js index a835df2a2..c6287a8a0 100644 --- a/e2e/paths/10-travel/02_basic_data_and_log.spec.js +++ b/e2e/paths/10-travel/02_basic_data_and_log.spec.js @@ -24,7 +24,10 @@ describe('Travel basic data path', () => { }); it('should set a wrong delivery date then receive an error on submit', async() => { - await page.datePicker(selectors.travelBasicDada.deliveryDate, -1, null); + const lastMonth = new Date(); + lastMonth.setMonth(lastMonth.getMonth() - 1); + + await page.pickDate(selectors.travelBasicDada.deliveryDate, lastMonth); await page.waitToClick(selectors.travelBasicDada.save); const result = await page.waitForLastSnackbar(); diff --git a/e2e/paths/11-zone/01_basic-data.spec.js b/e2e/paths/11-zone/01_basic-data.spec.js index c63bb8321..4bb89e459 100644 --- a/e2e/paths/11-zone/01_basic-data.spec.js +++ b/e2e/paths/11-zone/01_basic-data.spec.js @@ -31,7 +31,7 @@ describe('Zone basic data path', () => { await page.clearInput(selectors.zoneBasicData.travelingDays); await page.write(selectors.zoneBasicData.travelingDays, '1'); await page.clearInput(selectors.zoneBasicData.closing); - await page.type(selectors.zoneBasicData.closing, '2100'); + await page.type(selectors.zoneBasicData.closing, '09:00PM'); await page.clearInput(selectors.zoneBasicData.price); await page.write(selectors.zoneBasicData.price, '999'); await page.clearInput(selectors.zoneBasicData.bonus); @@ -40,14 +40,13 @@ describe('Zone basic data path', () => { await page.write(selectors.zoneBasicData.inflation, '200'); await page.waitToClick(selectors.zoneBasicData.volumetric); await page.waitToClick(selectors.zoneBasicData.saveButton); - await page.waitForContentLoaded(); + const result = await page.waitForLastSnackbar(); + + expect(result).toEqual('Data saved!'); }); it('should now reload the section', async() => { await page.reloadSection('zone.card.basicData'); - let url = await page.expectURL('#!/zone/10/basic-data'); - - expect(url).toBe(true); }); it('should confirm the name was updated', async() => { diff --git a/front/core/components/snackbar/snackbar.js b/front/core/components/snackbar/snackbar.js index eb75f9ab8..9439198f0 100644 --- a/front/core/components/snackbar/snackbar.js +++ b/front/core/components/snackbar/snackbar.js @@ -6,9 +6,8 @@ import './style.scss'; * A simple component to show non-obstructive notifications to the user. */ export default class Controller extends Component { - constructor($element, $translate) { - super($element); - this.$translate = $translate; + constructor($element, $) { + super($element, $); this.snackbar = $element[0].firstChild; this.$snackbar = angular.element(this.snackbar); } @@ -19,38 +18,54 @@ export default class Controller extends Component { * @return {Object} Created snackbar shape */ createShape(data) { - let shape = document.createElement('div'); - shape.className = 'shape'; + let shape = Object.assign({ + nMessages: 1 + }, data); + + let element = document.createElement('div'); + element.className = 'shape'; + setTimeout(() => element.classList.add('shown'), 30); + shape.element = element; + + if (shape.type) + element.classList.add(shape.type); let button = document.createElement('button'); + button.addEventListener('click', () => this.onButtonClick(shape)); + element.appendChild(button); - let buttonText = data.actionText || this.$translate.instant('Hide'); + let buttonText = shape.actionText || this.$t('Hide'); buttonText = document.createTextNode(buttonText); button.appendChild(buttonText); - button.addEventListener('click', () => { - this.onButtonClick(shape); - }); - - shape.appendChild(button); - let shapeText = document.createElement('div'); shapeText.setAttribute('class', 'text'); - shape.appendChild(shapeText); + element.appendChild(shapeText); - let text = document.createTextNode(data.message); + let text = document.createTextNode(shape.message); shapeText.appendChild(text); - if (data.shapeType) - shape.classList.add(data.shapeType); + let chip = document.createElement('vn-chip'); + chip.className = 'warning small'; + chip.style.visibility = 'hidden'; - let parent = this.snackbar.querySelectorAll('.shape')[0]; + let chipWrapper = document.createElement('div'); + chip.append(chipWrapper); + + let span = document.createElement('span'); + chipWrapper.append(span); + + let chipText = document.createTextNode(shape.nMessages); + span.append(chipText); + + shapeText.appendChild(chip); + + let parent = this.snackbar.querySelector('.shape'); if (parent) - this.snackbar.insertBefore(shape, parent); + this.snackbar.insertBefore(element, parent); else - this.snackbar.appendChild(shape); - + this.snackbar.appendChild(element); return shape; } @@ -61,58 +76,28 @@ export default class Controller extends Component { * @param {Object} data The message data */ show(data) { - this.actionHandler = data.actionHandler; + let shape = this.lastShape; - let shape; + const isEqual = shape + && shape.type == data.type + && shape.message == data.message; - const lastShape = this.lastShape; - const lastShapeData = lastShape && lastShape.data; - const isEqual = lastShape && (lastShapeData.shapeType == data.shapeType && lastShapeData.message == data.message); + if (isEqual) { + shape.nMessages++; - if (lastShape && isEqual) { - shape = lastShape.element; + const chip = shape.element.querySelector('.text vn-chip'); + chip.style.visibility = 'visible'; - const shapeText = shape.querySelector('.text'); - let chip = shapeText.querySelector('vn-chip'); - - if (chip) { - const text = chip.querySelector('span'); - const number = parseInt(text.innerHTML); - - text.innerHTML = number + 1; - } else { - chip = document.createElement('vn-chip'); - chip.setAttribute('class', 'warning small'); - let parent = document.createElement('div'); - let span = document.createElement('span'); - let text = document.createTextNode(1); - span.append(text); - parent.append(span); - chip.append(parent); - - shapeText.appendChild(chip); - } - - lastShape.element.classList.add('shown'); - - if (this.hideTimeout) - clearTimeout(this.hideTimeout); - } else { + const span = chip.querySelector('span'); + span.innerHTML = shape.nMessages; + } else shape = this.createShape(data); - setTimeout(() => - shape.classList.add('shown'), 30); - } + clearTimeout(shape.hideTimeout); + shape.hideTimeout = setTimeout( + () => this.hide(shape), shape.timeout || 3000); - this.hideTimeout = setTimeout(() => { - this.hide(shape); - this.lastShape = null; - }, data.timeout || 3000); - - this.lastShape = { - data: data, - element: shape - }; + this.lastShape = shape; } /** @@ -121,8 +106,7 @@ export default class Controller extends Component { * @param {Object} data The message data */ showError(data) { - data.shapeType = 'error'; - + data.type = 'error'; this.show(data); } @@ -132,8 +116,7 @@ export default class Controller extends Component { * @param {Object} data The message data */ showSuccess(data) { - data.shapeType = 'success'; - + data.type = 'success'; this.show(data); } @@ -142,8 +125,11 @@ export default class Controller extends Component { * @param {Object} shape Snackbar element */ hide(shape) { - setTimeout(() => shape.classList.remove('shown'), 30); - setTimeout(() => shape.remove(), 250); + if (this.lastShape == shape) + this.lastShape = null; + + shape.element.classList.remove('shown'); + setTimeout(() => shape.element.remove(), 250); } onSnackbarClick(event) { @@ -151,13 +137,12 @@ export default class Controller extends Component { } onButtonClick(shape) { - if (this.actionHandler) - this.actionHandler(); + if (shape.actionHandler) + shape.actionHandler(); else this.hide(shape); } } -Controller.$inject = ['$element', '$translate']; ngModule.component('vnSnackbar', { template: require('./snackbar.html'), diff --git a/package-lock.json b/package-lock.json index 8648fe476..dd10182e3 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2098,6 +2098,13 @@ "extend": "^3.0.1", "split-array-stream": "^2.0.0", "stream-events": "^1.0.4" + }, + "dependencies": { + "arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" + } } }, "@google-cloud/projectify": { @@ -2138,6 +2145,11 @@ "xdg-basedir": "^3.0.0" }, "dependencies": { + "arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" + }, "mime": { "version": "2.4.4", "resolved": "https://registry.npmjs.org/mime/-/mime-2.4.4.tgz", @@ -3210,7 +3222,8 @@ "arrify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", + "dev": true }, "asn1": { "version": "0.2.4", @@ -7972,6 +7985,12 @@ "pinkie-promise": "^2.0.0" }, "dependencies": { + "arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", + "dev": true + }, "glob": { "version": "7.1.4", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", @@ -8327,20 +8346,6 @@ "kind-of": "^1.1.0" } }, - "glob": { - "version": "7.1.4", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", - "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==", - "dev": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, "jasmine": { "version": "2.99.0", "resolved": "https://registry.npmjs.org/jasmine/-/jasmine-2.99.0.tgz", @@ -8354,7 +8359,7 @@ }, "kind-of": { "version": "1.1.0", - "resolved": "http://registry.npmjs.org/kind-of/-/kind-of-1.1.0.tgz", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-1.1.0.tgz", "integrity": "sha1-FAo9LUGjbS78+pN3tiwk+ElaXEQ=", "dev": true }, @@ -8382,9 +8387,9 @@ } }, "xtend": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", - "integrity": "sha1-pcbVMr5lbiPbgg77lDofBJmNY68=", + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", "dev": true } } @@ -9990,7 +9995,7 @@ }, "jasmine-core": { "version": "2.99.1", - "resolved": "http://registry.npmjs.org/jasmine-core/-/jasmine-core-2.99.1.tgz", + "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-2.99.1.tgz", "integrity": "sha1-5kAN8ea1bhMLYcS80JPap/boyhU=", "dev": true }, From c254604572446d254a9a264a8b52108a7c3ebc99 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Tue, 24 Mar 2020 00:54:12 +0100 Subject: [PATCH 06/15] E2E fixes --- e2e/helpers/extensions.js | 109 +++++++++++++++++++------------------- 1 file changed, 55 insertions(+), 54 deletions(-) diff --git a/e2e/helpers/extensions.js b/e2e/helpers/extensions.js index cccf85391..820a1e1f0 100644 --- a/e2e/helpers/extensions.js +++ b/e2e/helpers/extensions.js @@ -1,4 +1,45 @@ +function checkVisibility(selector) { + let selectorMatches = document.querySelectorAll(selector); + let element = selectorMatches[0]; + + if (selectorMatches.length > 1) + throw new Error(`Multiple matches of ${selector} found`); + + let isVisible = false; + if (element) { + let eventHandler = event => { + event.preventDefault(); + isVisible = true; + }; + element.addEventListener('mouseover', eventHandler); + let rect = element.getBoundingClientRect(); + let x = rect.left + rect.width / 2; + let y = rect.top + rect.height / 2; + let elementInCenter = document.elementFromPoint(x, y); + let elementInTopLeft = document.elementFromPoint(rect.left, rect.top); + let elementInBottomRight = document.elementFromPoint(rect.right, rect.bottom); + + let e = new MouseEvent('mouseover', { + view: window, + bubbles: true, + cancelable: true, + }); + + if (elementInCenter) + elementInCenter.dispatchEvent(e); + + if (elementInTopLeft) + elementInTopLeft.dispatchEvent(e); + + if (elementInBottomRight) + elementInBottomRight.dispatchEvent(e); + + element.removeEventListener('mouseover', eventHandler); + } + return isVisible; +} + let actions = { clickIfExists: async function(selector) { let exists; @@ -189,7 +230,7 @@ let actions = { waitToClick: async function(selector) { await this.waitForSelector(selector); - await this.checkVisibility(selector); + await this.waitForFunction(checkVisibility, {}, selector); return await this.click(selector); }, @@ -209,52 +250,9 @@ let actions = { }, selector); }, - checkVisibility: async function(selector) { - return await this.evaluate(function(selector) { - let selectorMatches = document.querySelectorAll(selector); - let element = selectorMatches[0]; - - if (selectorMatches.length > 1) - throw new Error(`Multiple matches of ${selector} found`); - - let isVisible = false; - if (element) { - let eventHandler = event => { - event.preventDefault(); - isVisible = true; - }; - element.addEventListener('mouseover', eventHandler); - let rect = element.getBoundingClientRect(); - let x = rect.left + rect.width / 2; - let y = rect.top + rect.height / 2; - let elementInCenter = document.elementFromPoint(x, y); - let elementInTopLeft = document.elementFromPoint(rect.left, rect.top); - let elementInBottomRight = document.elementFromPoint(rect.right, rect.bottom); - - let e = new MouseEvent('mouseover', { - view: window, - bubbles: true, - cancelable: true, - }); - - if (elementInCenter) - elementInCenter.dispatchEvent(e); - - if (elementInTopLeft) - elementInTopLeft.dispatchEvent(e); - - if (elementInBottomRight) - elementInBottomRight.dispatchEvent(e); - - element.removeEventListener('mouseover', eventHandler); - } - return isVisible; - }, selector); - }, - isVisible: async function(selector) { await this.waitForSelector(selector); - return await this.checkVisibility(selector); + return await this.evaluate(checkVisibility, selector); }, waitImgLoad: async function(selector) { @@ -360,14 +358,17 @@ let actions = { pickDate: async function(selector, date) { date = date || new Date(); - date = date.toISOString().substr(0, 10); + + const tzoffset = date.getTimezoneOffset() * 60000; + const localIso = (new Date(date.getTime() - tzoffset)) + .toISOString(); await this.wait(selector); - await this.evaluate((selector, date) => { + await this.evaluate((selector, localIso) => { let input = document.querySelector(selector).$ctrl.input; - input.value = date; + input.value = localIso.substr(0, 10); input.dispatchEvent(new Event('change')); - }, selector, date); + }, selector, localIso); }, pickTime: async function(selector, time) { @@ -418,7 +419,7 @@ let actions = { .querySelectorAll('li'); }, selector); - await this.write('.vn-drop-down.vn-popover.vn-popup.shown vn-textfield', searchValue); + await this.write('.vn-drop-down.shown vn-textfield', searchValue); try { await this.waitForFunction((selector, searchValue) => { @@ -430,7 +431,7 @@ let actions = { }, {}, selector, searchValue); } catch (error) { let inputValue = await this.evaluate(() => { - return document.querySelector('.vn-drop-down.vn-popover.vn-popup.shown vn-textfield input').value; + return document.querySelector('.vn-drop-down.shown vn-textfield input').value; }); throw new Error(`${builtSelector} value is ${inputValue}! ${error}`); } @@ -532,9 +533,9 @@ let actions = { }, respondToDialog: async function(response) { - await this.waitForSelector('.vn-dialog.vn-popup.shown'); + await this.waitForSelector('.vn-dialog.shown'); const firstCount = await this.evaluate(text => { - const dialogs = document.querySelectorAll('.vn-dialog.vn-popup'); + const dialogs = document.querySelectorAll('.vn-dialog'); const dialogOnTop = dialogs[dialogs.length - 1]; const button = dialogOnTop.querySelector(`div.buttons [response="${text}"]`); button.click(); @@ -542,7 +543,7 @@ let actions = { }, response); this.waitForFunction(firstCount => { - const dialogs = document.querySelectorAll('.vn-dialog.vn-popup'); + const dialogs = document.querySelectorAll('.vn-dialog'); return dialogs.length < firstCount; }, {}, firstCount); }, From acf8c117b02cd185b6fdb33f0031916a2bc9c405 Mon Sep 17 00:00:00 2001 From: Carlos Jimenez Ruiz Date: Tue, 24 Mar 2020 10:48:16 +0100 Subject: [PATCH 07/15] small spec fixes --- e2e/paths/05-ticket/12_descriptor.spec.js | 2 +- e2e/paths/11-zone/01_basic-data.spec.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/e2e/paths/05-ticket/12_descriptor.spec.js b/e2e/paths/05-ticket/12_descriptor.spec.js index 0e3712c82..0302b9c86 100644 --- a/e2e/paths/05-ticket/12_descriptor.spec.js +++ b/e2e/paths/05-ticket/12_descriptor.spec.js @@ -58,7 +58,7 @@ describe('Ticket descriptor path', () => { it(`should search for the deleted ticket and check it's date`, async() => { await page.write(selectors.ticketsIndex.topbarSearch, '18'); await page.waitToClick(selectors.ticketsIndex.searchButton); - await page.expectURL('/summary'); + await page.waitForState('ticket.card.summary'); const result = await page.waitToGetProperty(selectors.ticketsIndex.searchResultDate, 'innerText'); expect(result).toContain(2000); diff --git a/e2e/paths/11-zone/01_basic-data.spec.js b/e2e/paths/11-zone/01_basic-data.spec.js index 4bb89e459..41b3782aa 100644 --- a/e2e/paths/11-zone/01_basic-data.spec.js +++ b/e2e/paths/11-zone/01_basic-data.spec.js @@ -31,7 +31,7 @@ describe('Zone basic data path', () => { await page.clearInput(selectors.zoneBasicData.travelingDays); await page.write(selectors.zoneBasicData.travelingDays, '1'); await page.clearInput(selectors.zoneBasicData.closing); - await page.type(selectors.zoneBasicData.closing, '09:00PM'); + await page.pickTime(selectors.zoneBasicData.closing, '21:00'); await page.clearInput(selectors.zoneBasicData.price); await page.write(selectors.zoneBasicData.price, '999'); await page.clearInput(selectors.zoneBasicData.bonus); From 68a4ed0f103200784b5ab110c2838f80d5a17f9a Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Tue, 24 Mar 2020 11:12:59 +0100 Subject: [PATCH 08/15] Some E2E timeouts removed --- e2e/helpers/extensions.js | 17 ++++++++++------- e2e/helpers/puppeteer.js | 17 +++++++++++------ 2 files changed, 21 insertions(+), 13 deletions(-) diff --git a/e2e/helpers/extensions.js b/e2e/helpers/extensions.js index 820a1e1f0..1ff0119fd 100644 --- a/e2e/helpers/extensions.js +++ b/e2e/helpers/extensions.js @@ -58,9 +58,9 @@ let actions = { return document.location.hash.includes(expectedHash); }, {}, expectedHash); } catch (error) { - throw new Error(`failed to reach URL containing: ${expectedHash}`); + throw new Error(`Failed to reach URL containing: ${expectedHash}`); } - await this.waitForContentLoaded(); + await this.waitForSpinnerLoad(); return true; }, @@ -123,8 +123,9 @@ let actions = { waitForState: async function(state) { await this.waitFor(state => { let $state = angular.element(document.body).injector().get('$state'); - return $state.is(state); + return !$state.transition && $state.is(state); }, {}, state); + await this.waitForSpinnerLoad(state); }, waitForTransition: async function() { @@ -152,7 +153,6 @@ let actions = { }, state); await this.waitForState(state); - await this.waitForContentLoaded(); }, reloadSection: async function(state) { @@ -172,7 +172,7 @@ let actions = { await this.write('vn-searchbar', searchValue); await this.waitToClick('vn-searchbar vn-icon[icon="search"]'); await this.waitForTransition(); - await this.waitForContentLoaded(); + await this.waitFor('.vn-descriptor'); }, getProperty: async function(selector, property) { @@ -334,7 +334,10 @@ let actions = { }, hideSnackbar: async function() { - await this.waitFor(300); // holds up for the snackbar to be visible for a small period of time. + // Holds up for the snackbar to be visible for a small period of time. + if (process.env.DEBUG) + await this.waitFor(300); + await this.evaluate(() => { let hideButton = document.querySelector('#shapes .shown button'); if (hideButton) @@ -549,7 +552,7 @@ let actions = { }, waitForContentLoaded: async function() { - await this.waitFor(250); + // await this.waitFor(250); } }; diff --git a/e2e/helpers/puppeteer.js b/e2e/helpers/puppeteer.js index 8aa3f72f8..1ea3c1c90 100644 --- a/e2e/helpers/puppeteer.js +++ b/e2e/helpers/puppeteer.js @@ -4,17 +4,22 @@ import {extendPage} from './extensions'; import {url as defaultURL} from './config'; export async function getBrowser() { - let headless = !process.env.E2E_SHOW; + const args = [ + `--no-sandbox`, + `--window-size=${ 1920 },${ 1080 }` + ]; + + if (process.env.DEBUG) + args.push('--auto-open-devtools-for-tabs'); + + const headless = !process.env.E2E_SHOW; const browser = await Puppeteer.launch({ - args: [ - '--no-sandbox', - `--window-size=${ 1920 },${ 1080 }`, - // '--auto-open-devtools-for-tabs' - ], + args, defaultViewport: null, headless: headless, slowMo: 0, // slow down by ms }); + let page = (await browser.pages())[0]; await page.evaluateOnNewDocument(() => { Object.defineProperty(navigator, 'language', { From 423f59dfb04d6e8c1a0da9e4bf1e03cd72d7c5ec Mon Sep 17 00:00:00 2001 From: Bernat Exposito Domenech Date: Tue, 24 Mar 2020 12:20:53 +0100 Subject: [PATCH 09/15] worker log --- db/changes/10162-fallas/00-acl.sql | 1 + db/changes/10162-fallas/00-workerLog.sql | 6 +++ modules/travel/back/models/travel.json | 2 +- modules/worker/back/model-config.json | 6 +++ modules/worker/back/models/worker-log.json | 58 ++++++++++++++++++++++ modules/worker/back/models/worker.json | 6 ++- modules/worker/front/basic-data/index.html | 5 +- modules/worker/front/basic-data/index.js | 2 +- modules/worker/front/index.js | 1 + modules/worker/front/locale/es.yml | 1 + modules/worker/front/routes.json | 8 ++- modules/worker/front/worker-log/index.html | 1 + modules/worker/front/worker-log/index.js | 15 ++++++ 13 files changed, 105 insertions(+), 7 deletions(-) create mode 100644 db/changes/10162-fallas/00-acl.sql create mode 100644 db/changes/10162-fallas/00-workerLog.sql create mode 100644 modules/worker/back/models/worker-log.json create mode 100644 modules/worker/front/worker-log/index.html create mode 100644 modules/worker/front/worker-log/index.js diff --git a/db/changes/10162-fallas/00-acl.sql b/db/changes/10162-fallas/00-acl.sql new file mode 100644 index 000000000..376788af1 --- /dev/null +++ b/db/changes/10162-fallas/00-acl.sql @@ -0,0 +1 @@ +INSERT INTO `salix`.`ACL` (`model`, `property`, `accessType`, `permission`, `principalType`, `principalId`) VALUES ('WorkerLog', '*', 'READ', 'ALLOW', 'ROLE', 'hr'); diff --git a/db/changes/10162-fallas/00-workerLog.sql b/db/changes/10162-fallas/00-workerLog.sql new file mode 100644 index 000000000..730b60aa5 --- /dev/null +++ b/db/changes/10162-fallas/00-workerLog.sql @@ -0,0 +1,6 @@ +ALTER TABLE `vn`.`workerLog` + ADD COLUMN `changedModel` VARCHAR(45) NULL DEFAULT NULL AFTER `description`, + ADD COLUMN `oldInstance` text CHARACTER SET utf8 COLLATE utf8_unicode_ci, + ADD COLUMN `newInstance` text CHARACTER SET utf8 COLLATE utf8_unicode_ci, + ADD COLUMN `changedModelId` int(11) DEFAULT NULL, + ADD COLUMN `changedModelValue` varchar(45) CHARACTER SET utf8 COLLATE utf8_unicode_ci DEFAULT NULL; \ No newline at end of file diff --git a/modules/travel/back/models/travel.json b/modules/travel/back/models/travel.json index 0eafe4010..aebf4e3cd 100644 --- a/modules/travel/back/models/travel.json +++ b/modules/travel/back/models/travel.json @@ -7,7 +7,7 @@ }, "options": { "mysql": { - "table": "travel" + "table": "travel" } }, "properties": { diff --git a/modules/worker/back/model-config.json b/modules/worker/back/model-config.json index 884759bc9..e91e8b0fc 100644 --- a/modules/worker/back/model-config.json +++ b/modules/worker/back/model-config.json @@ -52,5 +52,11 @@ }, "Device": { "dataSource": "vn" + }, + "WorkerLog": { + "dataSource": "vn" } } + + + diff --git a/modules/worker/back/models/worker-log.json b/modules/worker/back/models/worker-log.json new file mode 100644 index 000000000..f100f3486 --- /dev/null +++ b/modules/worker/back/models/worker-log.json @@ -0,0 +1,58 @@ +{ + "name": "WorkerLog", + "base": "VnModel", + "options": { + "mysql": { + "table": "workerLog" + } + }, + "properties": { + "id": { + "id": true, + "type": "Number", + "forceId": false + }, + "originFk": { + "type": "Number", + "required": true + }, + "userFk": { + "type": "Number" + }, + "action": { + "type": "String", + "required": true + }, + "changedModel": { + "type": "String" + }, + "oldInstance": { + "type": "Object" + }, + "newInstance": { + "type": "Object" + }, + "creationDate": { + "type": "Date" + }, + "changedModelId": { + "type": "String" + }, + "changedModelValue": { + "type": "String" + }, + "description": { + "type": "String" + } + }, + "relations": { + "user": { + "type": "belongsTo", + "model": "Account", + "foreignKey": "userFk" + } + }, + "scope": { + "order": ["creationDate DESC", "id DESC"] + } +} diff --git a/modules/worker/back/models/worker.json b/modules/worker/back/models/worker.json index 7456a3caa..6af7e8608 100644 --- a/modules/worker/back/models/worker.json +++ b/modules/worker/back/models/worker.json @@ -1,7 +1,11 @@ { "name": "Worker", "description": "Company employees", - "base": "VnModel", + "base": "Loggable", + "log": { + "model":"WorkerLog", + "showField": "firstName" + }, "options": { "mysql": { "table": "worker" diff --git a/modules/worker/front/basic-data/index.html b/modules/worker/front/basic-data/index.html index 67439b350..bdc309c00 100644 --- a/modules/worker/front/basic-data/index.html +++ b/modules/worker/front/basic-data/index.html @@ -1,10 +1,9 @@ + + save="patch">
diff --git a/modules/worker/front/basic-data/index.js b/modules/worker/front/basic-data/index.js index 28107dc12..bf38ce848 100644 --- a/modules/worker/front/basic-data/index.js +++ b/modules/worker/front/basic-data/index.js @@ -6,7 +6,7 @@ class Controller { } onSubmit() { - this.$.watcher.submit() + return this.$.watcher.submit() .then(() => this.card.reload()); } } diff --git a/modules/worker/front/index.js b/modules/worker/front/index.js index f703e7c21..00b4bdaa8 100644 --- a/modules/worker/front/index.js +++ b/modules/worker/front/index.js @@ -13,6 +13,7 @@ import './department'; import './calendar'; import './time-control'; import './log'; +import './worker-log'; import './dms/index'; import './dms/create'; import './dms/edit'; diff --git a/modules/worker/front/locale/es.yml b/modules/worker/front/locale/es.yml index 3fa727801..82535fe4e 100644 --- a/modules/worker/front/locale/es.yml +++ b/modules/worker/front/locale/es.yml @@ -18,3 +18,4 @@ Calendar: Calendario Search workers by id, firstName, lastName or user name: Buscar trabajadores por el identificador, nombre, apellidos o nombre de usuario Time control: Control de horario Data saved! User must access web: ¡Datos guardados! El usuario deberá acceder con su contraseña a la web para que los cambios surtan efecto. +Log: Historial \ No newline at end of file diff --git a/modules/worker/front/routes.json b/modules/worker/front/routes.json index d7eded94b..9aa214c5c 100644 --- a/modules/worker/front/routes.json +++ b/modules/worker/front/routes.json @@ -13,7 +13,8 @@ {"state": "worker.card.pbx", "icon": "icon-pbx"}, {"state": "worker.card.calendar", "icon": "icon-calendar"}, {"state": "worker.card.timeControl", "icon": "access_time"}, - {"state": "worker.card.dms.index", "icon": "cloud_upload"} + {"state": "worker.card.dms.index", "icon": "cloud_upload"}, + {"state": "worker.card.workerLog", "icon": "history"} ] }, "routes": [ @@ -51,6 +52,11 @@ "worker": "$ctrl.worker" }, "acl": ["hr"] + }, { + "url" : "/log", + "state": "worker.card.workerLog", + "component": "vn-worker-log", + "description": "Log" }, { "url": "/pbx", "state": "worker.card.pbx", diff --git a/modules/worker/front/worker-log/index.html b/modules/worker/front/worker-log/index.html new file mode 100644 index 000000000..b38a456cb --- /dev/null +++ b/modules/worker/front/worker-log/index.html @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/modules/worker/front/worker-log/index.js b/modules/worker/front/worker-log/index.js new file mode 100644 index 000000000..bd1e987c9 --- /dev/null +++ b/modules/worker/front/worker-log/index.js @@ -0,0 +1,15 @@ +import ngModule from '../module'; + +class Controller { + constructor($scope, $stateParams) { + this.$scope = $scope; + this.$stateParams = $stateParams; + } +} + +Controller.$inject = ['$scope', '$stateParams']; + +ngModule.component('vnWorkerLog', { + template: require('./index.html'), + controller: Controller, +}); From a52fcb587a6febada016fae8e940f32e8cac40d4 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Tue, 24 Mar 2020 14:10:07 +0100 Subject: [PATCH 10/15] drop-down e2e fix --- front/core/components/drop-down/index.js | 33 +++++++++++++++--------- 1 file changed, 21 insertions(+), 12 deletions(-) diff --git a/front/core/components/drop-down/index.js b/front/core/components/drop-down/index.js index 9f2dfe424..ed7de7179 100644 --- a/front/core/components/drop-down/index.js +++ b/front/core/components/drop-down/index.js @@ -29,13 +29,16 @@ export default class DropDown extends Popover { } set search(value) { - let oldValue = this._search; + function nullify(value) { + return value == '' || value == undefined ? null : value; + } + + let oldValue = nullify(this._search); this._search = value; if (!this.shown) return; - value = value == '' || value == null ? null : value; - oldValue = oldValue == '' || oldValue == null ? null : oldValue; + value = nullify(value); if (value === oldValue && this.modelData != null) return; if (value != null) @@ -45,7 +48,8 @@ export default class DropDown extends Popover { if (this.model) { this.model.clear(); - if (!this.data) { + + if (this.model instanceof CrudModel) { this.searchTimeout = this.$timeout(() => { this.refreshModel(); this.searchTimeout = null; @@ -353,6 +357,7 @@ export default class DropDown extends Popover { set model(value) { this.linkEvents({_model: value}, {dataChange: this.onDataChange}); this.onDataChange(); + this.search = this.search; } get url() { @@ -362,10 +367,9 @@ export default class DropDown extends Popover { set url(value) { this._url = value; if (value) { - this.model = new CrudModel(this.$q, this.$http); - this.model.autoLoad = false; - this.model.url = value; - this.model.$onInit(); + let model = new CrudModel(this.$q, this.$http); + model.url = value; + this.initModel(model); } } @@ -376,13 +380,18 @@ export default class DropDown extends Popover { set data(value) { this._data = value; if (value) { - this.model = new ArrayModel(this.$q, this.$filter); - this.model.autoLoad = false; - this.model.orgData = value; - this.model.$onInit(); + let model = new ArrayModel(this.$q, this.$filter); + model.orgData = value; + this.initModel(model); } } + initModel(model) { + model.autoLoad = false; + model.$onInit(); + this.model = model; + } + refreshModel() { let model = this.model; From 4f7e56788e81fee14f48aad47de48e15590e5c65 Mon Sep 17 00:00:00 2001 From: Carlos Jimenez Ruiz Date: Tue, 24 Mar 2020 16:49:36 +0100 Subject: [PATCH 11/15] replaced expectURL for waitForState in most cases --- e2e/helpers/extensions.js | 6 ---- e2e/paths/02-client/01_create_client.spec.js | 8 ++--- .../02-client/03_edit_fiscal_data.spec.js | 12 ++------ e2e/paths/02-client/05_add_address.spec.js | 16 +++------- .../02-client/06_add_address_notes.spec.js | 4 +-- e2e/paths/02-client/08_add_notes.spec.js | 8 ++--- e2e/paths/02-client/09_add_credit.spec.js | 4 +-- e2e/paths/02-client/10_add_greuge.spec.js | 4 +-- e2e/paths/02-client/13_log.spec.js | 5 +--- e2e/paths/02-client/14_balance.spec.js | 12 ++------ e2e/paths/02-client/19_summary.spec.js | 4 +-- e2e/paths/03-worker/01_summary.spec.js | 4 +-- e2e/paths/03-worker/04_time_control.spec.js | 8 ++--- e2e/paths/04-item/01_summary.spec.js | 4 +-- e2e/paths/04-item/08_create_and_clone.spec.js | 20 ++++--------- e2e/paths/04-item/09_regularize.spec.js | 28 +++++------------- e2e/paths/04-item/11_item_log.spec.js | 12 ++------ e2e/paths/04-item/13_request.spec.js | 4 +-- e2e/paths/05-ticket/05_tracking_state.spec.js | 8 ++--- .../05-ticket/06_basic_data_steps.spec.js | 8 ++--- e2e/paths/05-ticket/09_weekly.spec.js | 16 +++------- e2e/paths/05-ticket/10_request.spec.js | 5 +--- e2e/paths/05-ticket/11_diary.spec.js | 4 +-- e2e/paths/05-ticket/12_descriptor.spec.js | 20 ++++--------- e2e/paths/05-ticket/14_create_ticket.spec.js | 8 ++--- .../15_create_ticket_from_client.spec.js | 5 +--- e2e/paths/05-ticket/16_summary.spec.js | 8 ++--- e2e/paths/05-ticket/17_log.spec.js | 8 ++--- e2e/paths/06-claim/01_basic_data.spec.js | 4 +-- e2e/paths/06-claim/02_development.spec.js | 4 +-- e2e/paths/06-claim/03_detail.spec.js | 4 +-- e2e/paths/06-claim/05_summary.spec.js | 4 +-- e2e/paths/06-claim/06_descriptor.spec.js | 12 ++------ e2e/paths/07-order/01_summary.spec.js | 4 +-- e2e/paths/07-order/02_basic_data.spec.js | 16 +++------- e2e/paths/07-order/03_lines.spec.js | 7 ++--- e2e/paths/07-order/04_catalog.spec.js | 8 ++--- e2e/paths/08-route/01_summary.spec.js | 4 +-- e2e/paths/08-route/03_create.spec.js | 12 ++------ e2e/paths/09-invoice-out/01_summary.spec.js | 4 +-- .../09-invoice-out/02_descriptor.spec.js | 29 +++++-------------- e2e/paths/10-travel/01_thermograph.spec.js | 8 ++--- .../10-travel/02_basic_data_and_log.spec.js | 8 ++--- e2e/paths/11-zone/01_basic-data.spec.js | 4 +-- e2e/paths/12-entry/01_summary.spec.js | 4 +-- e2e/paths/12-entry/02_descriptor.spec.js | 28 +++++------------- 46 files changed, 105 insertions(+), 312 deletions(-) diff --git a/e2e/helpers/extensions.js b/e2e/helpers/extensions.js index 1ff0119fd..136a24905 100644 --- a/e2e/helpers/extensions.js +++ b/e2e/helpers/extensions.js @@ -416,12 +416,6 @@ let actions = { let builtSelector = await this.selectorFormater(selector); await this.waitToClick(selector); - await this.waitForSelector(selector => { - document - .querySelector(`${selector} vn-drop-down`).$ctrl.content - .querySelectorAll('li'); - }, selector); - await this.write('.vn-drop-down.shown vn-textfield', searchValue); try { diff --git a/e2e/paths/02-client/01_create_client.spec.js b/e2e/paths/02-client/01_create_client.spec.js index 2de38d421..29a27884f 100644 --- a/e2e/paths/02-client/01_create_client.spec.js +++ b/e2e/paths/02-client/01_create_client.spec.js @@ -102,15 +102,11 @@ describe('Client create path', async() => { await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.clientsButton); await page.wait(selectors.clientsIndex.createClientButton); - let url = await page.expectURL('#!/client/index'); - - expect(url).toBe(true); + await page.waitForState('lient.index'); }); it(`should search for the user Carol Danvers to confirm it exists`, async() => { await page.accessToSearchResult('Carol Danvers'); - let url = await page.expectURL('#!/client/114/summary'); - - expect(url).toBe(true); + await page.waitForState('client.card.summary'); }); }); diff --git a/e2e/paths/02-client/03_edit_fiscal_data.spec.js b/e2e/paths/02-client/03_edit_fiscal_data.spec.js index 4cd54b87d..10a29cdfa 100644 --- a/e2e/paths/02-client/03_edit_fiscal_data.spec.js +++ b/e2e/paths/02-client/03_edit_fiscal_data.spec.js @@ -36,9 +36,7 @@ describe('Client Edit fiscalData path', () => { it(`should click on the fiscal data button`, async() => { await page.waitToClick(selectors.clientFiscalData.fiscalDataButton); - let url = await page.expectURL('fiscal-data'); - - expect(url).toBe(true); + await page.waitForState('client.card.fiscalData'); }); it('should not be able to edit the verified data checkbox', async() => { @@ -124,9 +122,7 @@ describe('Client Edit fiscalData path', () => { // confirm all addresses have now EQtax checked step 1 it(`should click on the addresses button to access to the client's addresses`, async() => { await page.waitToClick(selectors.clientAddresses.addressesButton); - let url = await page.expectURL('/address/index'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.index'); }); // confirm all addresses have now EQtax checked step 2 @@ -261,9 +257,7 @@ describe('Client Edit fiscalData path', () => { // confirm invoice by address checkbox gets checked if the EQtax differs between addresses step 1 it(`should click on the addresses button to access to the client's addresses`, async() => { await page.waitToClick(selectors.clientAddresses.addressesButton); - let url = await page.expectURL('/address/index'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.index'); }); // confirm invoice by address checkbox gets checked if the EQtax differs between addresses step 2 diff --git a/e2e/paths/02-client/05_add_address.spec.js b/e2e/paths/02-client/05_add_address.spec.js index c9228e1cf..f22798453 100644 --- a/e2e/paths/02-client/05_add_address.spec.js +++ b/e2e/paths/02-client/05_add_address.spec.js @@ -18,9 +18,7 @@ describe('Client Add address path', () => { it(`should click on the add new address button to access to the new address form`, async() => { await page.waitToClick(selectors.clientAddresses.createAddress); - let url = await page.expectURL('address/create'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.create'); }); it('should receive an error after clicking save button as consignee, street and town fields are empty', async() => { @@ -72,9 +70,7 @@ describe('Client Add address path', () => { }); it(`should navigate back to the addresses index`, async() => { - let url = await page.expectURL('/address/index'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.index'); }); it(`should confirm the new address exists and it's the default one`, async() => { @@ -101,9 +97,7 @@ describe('Client Add address path', () => { it(`should click on the edit icon of the default address`, async() => { await page.waitForTextInElement(selectors.clientAddresses.defaultAddress, 'Somewhere in Thailand'); await page.waitToClick(selectors.clientAddresses.firstEditAddress); - let url = await page.expectURL('/edit'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.edit'); }); it(`should click on the active checkbox and receive an error to save it because it is the default address`, async() => { @@ -119,8 +113,6 @@ describe('Client Add address path', () => { await page.waitForSelector('#shapes .shown', {hidden: true}); await page.waitToClick(selectors.clientAddresses.cancelEditAddressButton); await page.waitToClick('.vn-confirm.shown button[response="accept"]'); - let url = await page.expectURL('address/index'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.index'); }); }); diff --git a/e2e/paths/02-client/06_add_address_notes.spec.js b/e2e/paths/02-client/06_add_address_notes.spec.js index 58a949698..abfa1ae34 100644 --- a/e2e/paths/02-client/06_add_address_notes.spec.js +++ b/e2e/paths/02-client/06_add_address_notes.spec.js @@ -19,9 +19,7 @@ describe('Client add address notes path', () => { it(`should click on the edit icon of the default address`, async() => { await page.waitForTextInElement(selectors.clientAddresses.defaultAddress, '20 Ingram Street'); await page.waitToClick(selectors.clientAddresses.firstEditAddress); - let url = await page.expectURL('/edit'); - - expect(url).toBe(true); + await page.waitForState('client.card.address.edit'); }); it('should not save a description without observation type', async() => { diff --git a/e2e/paths/02-client/08_add_notes.spec.js b/e2e/paths/02-client/08_add_notes.spec.js index b759cbd07..3d6a8a915 100644 --- a/e2e/paths/02-client/08_add_notes.spec.js +++ b/e2e/paths/02-client/08_add_notes.spec.js @@ -17,16 +17,12 @@ describe('Client Add notes path', () => { }); it(`should reach the notes index`, async() => { - let url = await page.expectURL('/note'); - - expect(url).toBe(true); + await page.waitForState('client.card.note.index'); }); it(`should click on the add note button`, async() => { await page.waitToClick(selectors.clientNotes.addNoteFloatButton); - let url = await page.expectURL('/note/create'); - - expect(url).toBe(true); + await page.waitForState('client.card.note.create'); }); it(`should create a note`, async() => { diff --git a/e2e/paths/02-client/09_add_credit.spec.js b/e2e/paths/02-client/09_add_credit.spec.js index 05c50e809..639d850f6 100644 --- a/e2e/paths/02-client/09_add_credit.spec.js +++ b/e2e/paths/02-client/09_add_credit.spec.js @@ -18,9 +18,7 @@ describe('Client Add credit path', () => { it(`should click on the add credit button`, async() => { await page.waitToClick(selectors.clientCredit.addCreditFloatButton); - let url = await page.expectURL('/credit/create'); - - expect(url).toBe(true); + await page.waitForState('client.card.credit.create'); }); it(`should edit the credit`, async() => { diff --git a/e2e/paths/02-client/10_add_greuge.spec.js b/e2e/paths/02-client/10_add_greuge.spec.js index c934a42f1..1dda319be 100644 --- a/e2e/paths/02-client/10_add_greuge.spec.js +++ b/e2e/paths/02-client/10_add_greuge.spec.js @@ -18,9 +18,7 @@ describe('Client Add greuge path', () => { it(`should click on the add greuge button`, async() => { await page.waitToClick(selectors.clientGreuge.addGreugeFloatButton); - let url = await page.expectURL('greuge/create'); - - expect(url).toBe(true); + await page.waitForState('client.card.greuge.create'); }); it(`should receive an error if all fields are empty but date and type on submit`, async() => { diff --git a/e2e/paths/02-client/13_log.spec.js b/e2e/paths/02-client/13_log.spec.js index 462d66347..fc4b98b8b 100644 --- a/e2e/paths/02-client/13_log.spec.js +++ b/e2e/paths/02-client/13_log.spec.js @@ -27,9 +27,7 @@ describe('Client log path', () => { it('should navigate to the log section', async() => { await page.waitToClick(selectors.clientLog.logButton); - let url = await page.expectURL('log'); - - expect(url).toBe(true); + await page.waitForState('client.card.log'); }); it('should check the previous value of the last logged change', async() => { @@ -46,7 +44,6 @@ describe('Client log path', () => { let lastModificationCurrentValue = await page. waitToGetProperty(selectors.clientLog.lastModificationCurrentValue, 'innerText'); - expect(lastModificationPreviousValue).toEqual('name: DavidCharlesHaller'); expect(lastModificationCurrentValue).toEqual('name: this is a test'); }); diff --git a/e2e/paths/02-client/14_balance.spec.js b/e2e/paths/02-client/14_balance.spec.js index ef7930c8d..87dc84a8e 100644 --- a/e2e/paths/02-client/14_balance.spec.js +++ b/e2e/paths/02-client/14_balance.spec.js @@ -41,9 +41,7 @@ describe('Client balance path', () => { it('should click the new payment button', async() => { await page.closePopup(); await page.reloadSection('client.card.balance.index'); - let url = await page.expectURL('/balance'); - - expect(url).toBe(true); + await page.waitForState('client.card.balance.index'); }); it('should create a new payment that clears the debt', async() => { @@ -110,17 +108,13 @@ describe('Client balance path', () => { await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.clientsButton); await page.wait(selectors.clientsIndex.createClientButton); - let url = await page.expectURL('#!/client/index'); - - expect(url).toBe(true); + await page.waitForState('client.index'); }); it('should now search for the user Petter Parker', async() => { await page.accessToSearchResult('Petter Parker'); await page.waitToClick(selectors.clientBalance.balanceButton); - let url = await page.expectURL('/balance'); - - expect(url).toBe(true); + await page.waitForState('client.card.balance.index'); }); it('should not be able to click the new payment button as it isnt present', async() => { diff --git a/e2e/paths/02-client/19_summary.spec.js b/e2e/paths/02-client/19_summary.spec.js index 11b5a298e..ab39154cf 100644 --- a/e2e/paths/02-client/19_summary.spec.js +++ b/e2e/paths/02-client/19_summary.spec.js @@ -17,9 +17,7 @@ describe('Client summary path', () => { }); it('should reach the first route summary section', async() => { - let url = await page.expectURL('#!/client/102/summary'); - - expect(url).toBe(true); + await page.waitForState('client.card.summary'); }); it('should display details from the client on the header', async() => { diff --git a/e2e/paths/03-worker/01_summary.spec.js b/e2e/paths/03-worker/01_summary.spec.js index 86a95eee3..4ea87481a 100644 --- a/e2e/paths/03-worker/01_summary.spec.js +++ b/e2e/paths/03-worker/01_summary.spec.js @@ -16,9 +16,7 @@ describe('Worker summary path', () => { }); it('should reach the employee summary section', async() => { - const url = await page.expectURL('#!/worker/3/summary'); - - expect(url).toBe(true); + await page.waitForState('worker.card.summary'); }); it('should check the summary contains the name and userName on the header', async() => { diff --git a/e2e/paths/03-worker/04_time_control.spec.js b/e2e/paths/03-worker/04_time_control.spec.js index 36aaca61e..36340e880 100644 --- a/e2e/paths/03-worker/04_time_control.spec.js +++ b/e2e/paths/03-worker/04_time_control.spec.js @@ -316,16 +316,12 @@ describe('Worker time control path', () => { it('should search for a worker and access to its summary', async() => { await page.accessToSearchResult('HankPym'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('worker.card.summary'); }); it('should access to the time control section', async() => { await page.accessToSection('worker.card.timeControl'); - let url = await page.expectURL('/time-control'); - - expect(url).toBe(true); + await page.waitForState('worker.card.timeControl'); }); it('should lovingly scan in Hank Pym', async() => { diff --git a/e2e/paths/04-item/01_summary.spec.js b/e2e/paths/04-item/01_summary.spec.js index 6fd4e9c13..6f2c2c926 100644 --- a/e2e/paths/04-item/01_summary.spec.js +++ b/e2e/paths/04-item/01_summary.spec.js @@ -103,9 +103,7 @@ describe('Item summary path', () => { it(`should navigate to the one of the items detailed section`, async() => { await page.accessToSearchResult('Melee weapon combat fist 15cm'); - let url = await page.expectURL('summary'); - - expect(url).toBe(true); + await page.waitForState('item.card.summary'); }); it(`should check the descritor edit button is not visible for employee`, async() => { diff --git a/e2e/paths/04-item/08_create_and_clone.spec.js b/e2e/paths/04-item/08_create_and_clone.spec.js index d06ef4682..73249a0b9 100644 --- a/e2e/paths/04-item/08_create_and_clone.spec.js +++ b/e2e/paths/04-item/08_create_and_clone.spec.js @@ -27,23 +27,17 @@ describe('Item Create/Clone path', () => { it('should access to the create item view by clicking the create floating button', async() => { await page.waitToClick(selectors.itemsIndex.createItemButton); - let url = await page.expectURL('#!/item/create'); - - expect(url).toBe(true); + await page.waitForState('item.create'); }); it('should return to the item index by clickig the cancel button', async() => { await page.waitToClick(selectors.itemCreateView.cancelButton); - let url = await page.expectURL('#!/item/index'); - - expect(url).toBe(true); + await page.waitForState('item.index'); }); it('should now access to the create item view by clicking the create floating button', async() => { await page.waitToClick(selectors.itemsIndex.createItemButton); - let url = await page.expectURL('#!/item/create'); - - expect(url).toBe(true); + await page.waitForState('item.create'); }); it('should create the Infinity Gauntlet item', async() => { @@ -87,9 +81,7 @@ describe('Item Create/Clone path', () => { it('should return to the items index by clicking the return to items button', async() => { await page.waitToClick(selectors.itemBasicData.goToItemIndexButton); await page.wait(selectors.itemsIndex.createItemButton); - let url = await page.expectURL('#!/item/index'); - - expect(url).toBe(true); + await page.waitForState('item.index'); }); it(`should search for the item Infinity Gauntlet`, async() => { @@ -106,9 +98,7 @@ describe('Item Create/Clone path', () => { await page.waitForTextInElement(selectors.itemsIndex.searchResult, 'Infinity Gauntlet'); await page.waitToClick(selectors.itemsIndex.searchResultCloneButton); await page.waitToClick(selectors.itemsIndex.acceptClonationAlertButton); - let url = await page.expectURL('tags'); - - expect(url).toBe(true); + await page.waitForState('item.tags'); }); it('should search for the item Infinity Gauntlet and find two', async() => { diff --git a/e2e/paths/04-item/09_regularize.spec.js b/e2e/paths/04-item/09_regularize.spec.js index 18f182e74..a37d97fa3 100644 --- a/e2e/paths/04-item/09_regularize.spec.js +++ b/e2e/paths/04-item/09_regularize.spec.js @@ -34,9 +34,7 @@ describe('Item regularize path', () => { it('should search for an specific item', async() => { await page.accessToSearchResult('Ranged weapon pistol 9mm'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('item.card.summary'); }); it('should open the regularize dialog and check the warehouse matches the local user settings', async() => { @@ -63,9 +61,7 @@ describe('Item regularize path', () => { page.waitForNavigation({waitUntil: ['load', 'networkidle0', 'domcontentloaded']}), page.waitToClick(selectors.globalItems.ticketsButton) ]); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should clear the user local settings now', async() => { @@ -80,9 +76,7 @@ describe('Item regularize path', () => { it('should search for the ticket with alias missing', async() => { await page.keyboard.press('Escape'); await page.accessToSearchResult('missing'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it(`should check the ticket sale quantity is showing a negative value`, async() => { @@ -104,16 +98,12 @@ describe('Item regularize path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.itemsButton); - let url = await page.expectURL('#!/item/index'); - - expect(url).toBe(true); + await page.waitForState('item.index'); }); it('should search for the item once again', async() => { await page.accessToSearchResult('Ranged weapon pistol 9mm'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('item.card.summary'); }); it('should regularize the item once more', async() => { @@ -135,16 +125,12 @@ describe('Item regularize path', () => { page.waitToClick(selectors.globalItems.ticketsButton) ]); await page.waitForTransitionEnd('vn-searchbar'); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should search for the ticket with id 25 once again', async() => { await page.accessToSearchResult('25'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it(`should check the ticket contains now two sales`, async() => { diff --git a/e2e/paths/04-item/11_item_log.spec.js b/e2e/paths/04-item/11_item_log.spec.js index 213365c12..82800b9b8 100644 --- a/e2e/paths/04-item/11_item_log.spec.js +++ b/e2e/paths/04-item/11_item_log.spec.js @@ -25,9 +25,7 @@ describe('Item log path', () => { it('should access to the create item view by clicking the create floating button', async() => { await page.waitToClick(selectors.itemsIndex.createItemButton); - let url = await page.expectURL('#!/item/create'); - - expect(url).toBe(true); + await page.waitForState('item.create'); }); it('should create the Knowledge artifact item', async() => { @@ -44,17 +42,13 @@ describe('Item log path', () => { it('should return to the items index by clicking the return to items button', async() => { await page.waitToClick(selectors.itemBasicData.goToItemIndexButton); await page.wait(selectors.itemsIndex.createItemButton); - let url = await page.expectURL('#!/item/index'); - - expect(url).toBe(true); + await page.waitForState('item.index'); }); it(`should search for the created item and navigate to it's log section`, async() => { await page.accessToSearchResult('Knowledge artifact'); await page.accessToSection('item.card.log'); - let url = await page.expectURL('/log'); - - expect(url).toBe(true); + await page.waitForState('item.card.log'); }); it(`should confirm the log is showing 5 entries`, async() => { diff --git a/e2e/paths/04-item/13_request.spec.js b/e2e/paths/04-item/13_request.spec.js index d6aecbb48..2deabb20b 100644 --- a/e2e/paths/04-item/13_request.spec.js +++ b/e2e/paths/04-item/13_request.spec.js @@ -16,9 +16,7 @@ describe('Item request path', () => { }); it('should reach the item request section', async() => { - const result = await page.expectURL('/item/request'); - - expect(result).toBe(true); + await page.waitForState('item.request'); }); it('should fill the id and quantity then check the concept was updated', async() => { diff --git a/e2e/paths/05-ticket/05_tracking_state.spec.js b/e2e/paths/05-ticket/05_tracking_state.spec.js index 108e8776f..2623966be 100644 --- a/e2e/paths/05-ticket/05_tracking_state.spec.js +++ b/e2e/paths/05-ticket/05_tracking_state.spec.js @@ -21,9 +21,7 @@ describe('Ticket Create new tracking state path', () => { it('should access to the create state view by clicking the create floating button', async() => { await page.waitToClick(selectors.ticketTracking.createStateButton); await page.waitForSelector(selectors.createStateView.state, {visible: true}); - let url = await page.expectURL('tracking/edit'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.tracking.edit'); }); it(`should attempt create a new state but receive an error if state is empty`, async() => { @@ -51,9 +49,7 @@ describe('Ticket Create new tracking state path', () => { it('should now access to the create state view by clicking the create floating button', async() => { await page.waitToClick(selectors.ticketTracking.createStateButton); - let url = await page.expectURL('tracking/edit'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.tracking.edit'); }); it(`should attemp to create an state for which salesPerson doesn't have permissions`, async() => { diff --git a/e2e/paths/05-ticket/06_basic_data_steps.spec.js b/e2e/paths/05-ticket/06_basic_data_steps.spec.js index de78b9fa7..3191673a5 100644 --- a/e2e/paths/05-ticket/06_basic_data_steps.spec.js +++ b/e2e/paths/05-ticket/06_basic_data_steps.spec.js @@ -68,9 +68,7 @@ describe('Ticket Edit basic data path', () => { it(`should click next`, async() => { await page.waitToClick(selectors.ticketBasicData.nextStepButton); - let url = await page.expectURL('data/step-two'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.basicData.stepTwo'); }); it(`should have a price diference`, async() => { @@ -83,8 +81,6 @@ describe('Ticket Edit basic data path', () => { it(`should select a new reason for the changes made then click on finalize`, async() => { await page.waitToClick(selectors.ticketBasicData.chargesReason); await page.waitToClick(selectors.ticketBasicData.finalizeButton); - let url = await page.expectURL('summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); }); diff --git a/e2e/paths/05-ticket/09_weekly.spec.js b/e2e/paths/05-ticket/09_weekly.spec.js index 9213afd1d..1629107fb 100644 --- a/e2e/paths/05-ticket/09_weekly.spec.js +++ b/e2e/paths/05-ticket/09_weekly.spec.js @@ -41,9 +41,7 @@ describe('Ticket descriptor path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.ticketsButton); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should confirm the ticket 11 was added to thursday', async() => { @@ -57,16 +55,12 @@ describe('Ticket descriptor path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.ticketsButton); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should now search for the ticket 11', async() => { await page.accessToSearchResult('11'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it('should add the ticket to saturday turn using the descriptor more menu', async() => { @@ -82,9 +76,7 @@ describe('Ticket descriptor path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.ticketsButton); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should confirm the ticket 11 was added on saturday', async() => { diff --git a/e2e/paths/05-ticket/10_request.spec.js b/e2e/paths/05-ticket/10_request.spec.js index 737d69048..2bb0cbb73 100644 --- a/e2e/paths/05-ticket/10_request.spec.js +++ b/e2e/paths/05-ticket/10_request.spec.js @@ -30,13 +30,10 @@ describe('Ticket purchase request path', () => { }); it('should have been redirected to the request index', async() => { - let url = await page.expectURL('/request'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.request.index'); }); it(`should edit the third request quantity as it's state is still new`, async() => { - await page.waitFor(2000); // looks like it needs more than a single second some times to load await page.write(selectors.ticketRequests.thirdRequestQuantity, '9'); await page.keyboard.press('Enter'); const result = await page.waitForLastSnackbar(); diff --git a/e2e/paths/05-ticket/11_diary.spec.js b/e2e/paths/05-ticket/11_diary.spec.js index b529ee1ff..5e900fd25 100644 --- a/e2e/paths/05-ticket/11_diary.spec.js +++ b/e2e/paths/05-ticket/11_diary.spec.js @@ -28,7 +28,7 @@ xdescribe('Ticket diary path', () => { it(`should click on the search result to access to the ticket summary`, async() => { await page.waitForTextInElement(selectors.ticketsIndex.searchResult, 'Bat cave'); await page.waitToClick(selectors.ticketsIndex.searchResult); - let url = await page.expectURL('/summary'); + let url = await page.expectURL('/summary'); // use waitForState instead expect(url).toBe(true); }); @@ -37,7 +37,7 @@ xdescribe('Ticket diary path', () => { await page.waitToClick(selectors.ticketSummary.firstSaleItemId); await page.waitForTransitionEnd('.vn-popover'); await page.waitToClick(selectors.ticketSummary.popoverDiaryButton); - let url = await page.expectURL('/diary'); + let url = await page.expectURL('/diary'); // use waitForState instead expect(url).toBe(true); }); diff --git a/e2e/paths/05-ticket/12_descriptor.spec.js b/e2e/paths/05-ticket/12_descriptor.spec.js index 0302b9c86..ce9f064dd 100644 --- a/e2e/paths/05-ticket/12_descriptor.spec.js +++ b/e2e/paths/05-ticket/12_descriptor.spec.js @@ -18,9 +18,7 @@ describe('Ticket descriptor path', () => { describe('Delete ticket', () => { it('should search for an specific ticket', async() => { await page.accessToSearchResult('18'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it(`should update the shipped hour using the descriptor menu`, async() => { @@ -50,9 +48,7 @@ describe('Ticket descriptor path', () => { }); it('should have been relocated to the ticket index', async() => { - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it(`should search for the deleted ticket and check it's date`, async() => { @@ -68,9 +64,7 @@ describe('Ticket descriptor path', () => { describe('add stowaway', () => { it('should search for a ticket', async() => { await page.accessToSearchResult('16'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it('should open the add stowaway dialog', async() => { @@ -101,9 +95,7 @@ describe('Ticket descriptor path', () => { it(`should navigate back to the added ticket using the descriptors ship button`, async() => { await page.waitToClick(selectors.ticketDescriptor.shipButton); - let url = await page.expectURL('#!/ticket/17/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it('should delete the stowaway', async() => { @@ -127,9 +119,7 @@ describe('Ticket descriptor path', () => { await page.loginAndModule('adminBoss', 'ticket'); await page.accessToSearchResult(invoiceableTicketId); - let url = await page.expectURL(`ticket/${invoiceableTicketId}/summary`); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it(`should make sure the ticket doesn't have an invoiceOutFk yet`, async() => { diff --git a/e2e/paths/05-ticket/14_create_ticket.spec.js b/e2e/paths/05-ticket/14_create_ticket.spec.js index c44125120..176e89930 100644 --- a/e2e/paths/05-ticket/14_create_ticket.spec.js +++ b/e2e/paths/05-ticket/14_create_ticket.spec.js @@ -17,9 +17,7 @@ describe('Ticket create path', () => { it('should open the new ticket form', async() => { await page.waitToClick(selectors.ticketsIndex.newTicketButton); - let url = await page.expectURL('#!/ticket/create'); - - expect(url).toBe(true); + await page.waitForState('ticket.create'); }); it('should succeed to create a ticket', async() => { @@ -38,8 +36,6 @@ describe('Ticket create path', () => { }); it('should check the url is now the summary of the ticket', async() => { - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); }); diff --git a/e2e/paths/05-ticket/15_create_ticket_from_client.spec.js b/e2e/paths/05-ticket/15_create_ticket_from_client.spec.js index 28c11de3a..a68ce894e 100644 --- a/e2e/paths/05-ticket/15_create_ticket_from_client.spec.js +++ b/e2e/paths/05-ticket/15_create_ticket_from_client.spec.js @@ -19,9 +19,7 @@ describe('Ticket create from client path', () => { it('should click the create simple ticket on the descriptor menu', async() => { await page.waitToClick(selectors.clientDescriptor.moreMenu); await page.waitToClick(selectors.clientDescriptor.simpleTicketButton); - let url = await page.expectURL('clientFk=102'); - - expect(url).toBe(true); + await page.waitForState('ticket.create'); }); it('should check if the client details are the expected ones', async() => { @@ -31,7 +29,6 @@ describe('Ticket create from client path', () => { const address = await page .waitToGetProperty(selectors.createTicketView.address, 'value'); - expect(client).toContain('Petter Parker'); expect(address).toContain('20 Ingram Street'); }); diff --git a/e2e/paths/05-ticket/16_summary.spec.js b/e2e/paths/05-ticket/16_summary.spec.js index e7c6507d7..7ead648a2 100644 --- a/e2e/paths/05-ticket/16_summary.spec.js +++ b/e2e/paths/05-ticket/16_summary.spec.js @@ -18,9 +18,7 @@ describe('Ticket Summary path', () => { it('should navigate to the target ticket summary section', async() => { await page.loginAndModule('employee', 'ticket'); await page.accessToSearchResult(ticketId); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it(`should display details from the ticket and it's client on the top of the header`, async() => { @@ -75,9 +73,7 @@ describe('Ticket Summary path', () => { it('should log in as production then navigate to the summary of the same ticket', async() => { await page.loginAndModule('production', 'ticket'); await page.accessToSearchResult(ticketId); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.summary'); }); it('should click on the SET OK button', async() => { diff --git a/e2e/paths/05-ticket/17_log.spec.js b/e2e/paths/05-ticket/17_log.spec.js index 2008d022e..c677d2e62 100644 --- a/e2e/paths/05-ticket/17_log.spec.js +++ b/e2e/paths/05-ticket/17_log.spec.js @@ -19,9 +19,7 @@ describe('Ticket log path', () => { await page.loginAndModule('employee', 'ticket'); await page.accessToSearchResult(ticketId); await page.accessToSection('ticket.card.observation'); - let url = await page.expectURL('/observation'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.observation'); }); it('should create a new note for the test', async() => { @@ -36,9 +34,7 @@ describe('Ticket log path', () => { it('should navigate to the log section', async() => { await page.accessToSection('ticket.card.log'); - let url = await page.expectURL('/log'); - - expect(url).toBe(true); + await page.waitForState('ticket.card.log'); }); it('should set the viewport width to 1920 to see the table full width', async() => { diff --git a/e2e/paths/06-claim/01_basic_data.spec.js b/e2e/paths/06-claim/01_basic_data.spec.js index 2eb35b078..222cb558b 100644 --- a/e2e/paths/06-claim/01_basic_data.spec.js +++ b/e2e/paths/06-claim/01_basic_data.spec.js @@ -31,9 +31,7 @@ describe('Claim edit basic data path', () => { }); it(`should have been redirected to the next section of claims as the role is salesAssistant`, async() => { - let url = await page.expectURL('/detail'); - - expect(url).toBe(true); + await page.waitForState('claim.card.detail'); }); it('should confirm the claim state was edited', async() => { diff --git a/e2e/paths/06-claim/02_development.spec.js b/e2e/paths/06-claim/02_development.spec.js index 346f88581..970a801ee 100644 --- a/e2e/paths/06-claim/02_development.spec.js +++ b/e2e/paths/06-claim/02_development.spec.js @@ -32,9 +32,7 @@ describe('Claim development', () => { }); it(`should redirect to the next section of claims as the role is salesAssistant`, async() => { - let url = await page.expectURL('/action'); - - expect(url).toBe(true); + await page.waitForState('claim.card.action'); }); it('should edit a development', async() => { diff --git a/e2e/paths/06-claim/03_detail.spec.js b/e2e/paths/06-claim/03_detail.spec.js index cf758919e..93d2cba4c 100644 --- a/e2e/paths/06-claim/03_detail.spec.js +++ b/e2e/paths/06-claim/03_detail.spec.js @@ -56,7 +56,7 @@ xdescribe('Claim detail', () => { await page.loginAndModule('salesAssistant', 'claim'); await page.accessToSearchResult('1'); await page.accessToSection('claim.card.detail'); - let url = await page.expectURL('/detail'); + let url = await page.expectURL('/detail'); // replace with waitForState expect(url).toBe(true); }); @@ -99,7 +99,7 @@ xdescribe('Claim detail', () => { }); it(`should have been redirected to the next section in claims`, async() => { - let url = await page.expectURL('development'); + let url = await page.expectURL('development'); // replace with waitForState expect(url).toBe(true); }); diff --git a/e2e/paths/06-claim/05_summary.spec.js b/e2e/paths/06-claim/05_summary.spec.js index 9dab65954..c63e686cb 100644 --- a/e2e/paths/06-claim/05_summary.spec.js +++ b/e2e/paths/06-claim/05_summary.spec.js @@ -18,9 +18,7 @@ describe('claim Summary path', () => { it('should navigate to the target claim summary section', async() => { await page.loginAndModule('employee', 'claim'); await page.accessToSearchResult(claimId); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('claim.card.summary'); }); it(`should display details from the claim and it's client on the top of the header`, async() => { diff --git a/e2e/paths/06-claim/06_descriptor.spec.js b/e2e/paths/06-claim/06_descriptor.spec.js index 104f63945..ee49fe245 100644 --- a/e2e/paths/06-claim/06_descriptor.spec.js +++ b/e2e/paths/06-claim/06_descriptor.spec.js @@ -18,9 +18,7 @@ describe('claim Descriptor path', () => { it('should now navigate to the target claim summary section', async() => { await page.loginAndModule('employee', 'claim'); await page.accessToSearchResult(claimId); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('claim.card.summary'); }); it(`should not be able to see the delete claim button of the descriptor more menu`, async() => { @@ -31,9 +29,7 @@ describe('claim Descriptor path', () => { it(`should log in as salesAssistant and navigate to the target claim`, async() => { await page.loginAndModule('salesAssistant', 'claim'); await page.accessToSearchResult(claimId); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('claim.card.summary'); }); it(`should be able to see the delete claim button of the descriptor more menu`, async() => { @@ -50,9 +46,7 @@ describe('claim Descriptor path', () => { }); it(`should have been relocated to the claim index`, async() => { - let url = await page.expectURL('/claim/index'); - - expect(url).toBe(true); + await page.waitForState('claim.index'); }); it(`should search for the deleted claim to find no results`, async() => { diff --git a/e2e/paths/07-order/01_summary.spec.js b/e2e/paths/07-order/01_summary.spec.js index cba56bf70..f4bc44827 100644 --- a/e2e/paths/07-order/01_summary.spec.js +++ b/e2e/paths/07-order/01_summary.spec.js @@ -16,9 +16,7 @@ describe('Order summary path', () => { }); it('should reach the order summary section', async() => { - const url = await page.expectURL('#!/order/16/summary'); - - expect(url).toBe(true); + await page.waitForState('order.card.summary'); }); it('should check the summary contains the order id', async() => { diff --git a/e2e/paths/07-order/02_basic_data.spec.js b/e2e/paths/07-order/02_basic_data.spec.js index 733ccaa1a..d7bd01208 100644 --- a/e2e/paths/07-order/02_basic_data.spec.js +++ b/e2e/paths/07-order/02_basic_data.spec.js @@ -39,9 +39,7 @@ describe('Order edit basic data path', () => { await page.accessToSearchResult(orderId); await page.accessToSection('order.card.basicData'); await page.waitForSelector(selectors.orderBasicData.observation, {visible: true}); - let url = await page.expectURL(`#!/order/${orderId}/basic-data`); - - expect(url).toBe(true); + await page.waitForState('order.card.basicData'); }); it('should not be able to change anything', async() => { @@ -59,9 +57,7 @@ describe('Order edit basic data path', () => { await page.waitToClick(selectors.orderBasicData.acceptButton); await page.waitForContentLoaded(); await page.waitToClick(selectors.ordersIndex.createOrderButton); - let url = await page.expectURL('#!/order/create'); - - expect(url).toBe(true); + await page.waitForState('order.create'); }); it('should now create a new one', async() => { @@ -69,16 +65,12 @@ describe('Order edit basic data path', () => { await page.pickDate(selectors.createOrderView.landedDatePicker); await page.autocompleteSearch(selectors.createOrderView.agency, 'Other agency'); await page.waitToClick(selectors.createOrderView.createButton); - let url = await page.expectURL('/catalog'); - - expect(url).toBe(true); + await page.waitForState('order.card.catalog'); }); it('should navigate to the basic data section of the new order', async() => { await page.accessToSection('order.card.basicData'); - let url = await page.expectURL('/basic-data'); - - expect(url).toBe(true); + await page.waitForState('order.card.basicData'); }); it('should be able to modify all the properties', async() => { diff --git a/e2e/paths/07-order/03_lines.spec.js b/e2e/paths/07-order/03_lines.spec.js index 21fceac44..450e1b9c9 100644 --- a/e2e/paths/07-order/03_lines.spec.js +++ b/e2e/paths/07-order/03_lines.spec.js @@ -41,10 +41,7 @@ describe('Order lines', () => { it('should confirm the whole order and redirect to ticket index filtered by clientFk', async() => { await page.waitToClick(selectors.orderLine.confirmOrder); - let hashPartOne = await page.expectURL('ticket/index'); - let hashPartTwo = await page.expectURL('clientFk'); - - expect(hashPartOne).toBe(true); - expect(hashPartTwo).toBe(true); + await page.expectURL('ticket/index'); + await page.expectURL('clientFk'); }); }); diff --git a/e2e/paths/07-order/04_catalog.spec.js b/e2e/paths/07-order/04_catalog.spec.js index 8c3106f6c..0db313088 100644 --- a/e2e/paths/07-order/04_catalog.spec.js +++ b/e2e/paths/07-order/04_catalog.spec.js @@ -17,9 +17,7 @@ describe('Order catalog', () => { it('should open the create new order form', async() => { await page.waitToClick(selectors.ordersIndex.createOrderButton); - let url = await page.expectURL('order/create'); - - expect(url).toBe(true); + await page.waitForState('order.create'); }); it('should create a new order', async() => { @@ -27,9 +25,7 @@ describe('Order catalog', () => { await page.pickDate(selectors.createOrderView.landedDatePicker); await page.autocompleteSearch(selectors.createOrderView.agency, 'Other agency'); await page.waitToClick(selectors.createOrderView.createButton); - let url = await page.expectURL('/catalog'); - - expect(url).toBe(true); + await page.waitForState('order.card.catalog'); }); it('should add the realm and type filters and obtain results', async() => { diff --git a/e2e/paths/08-route/01_summary.spec.js b/e2e/paths/08-route/01_summary.spec.js index c062b9b08..02cc71f2f 100644 --- a/e2e/paths/08-route/01_summary.spec.js +++ b/e2e/paths/08-route/01_summary.spec.js @@ -17,9 +17,7 @@ describe('Route summary path', () => { }); it('should reach the first route summary section', async() => { - let url = await page.expectURL('#!/route/1/summary'); - - expect(url).toBe(true); + await page.waitForState('route.card.summary'); }); it(`should display details from the route on the header`, async() => { diff --git a/e2e/paths/08-route/03_create.spec.js b/e2e/paths/08-route/03_create.spec.js index c929e647f..dafccff7f 100644 --- a/e2e/paths/08-route/03_create.spec.js +++ b/e2e/paths/08-route/03_create.spec.js @@ -19,9 +19,7 @@ describe('Route create path', () => { it('should click on the add new route button and open the creation form', async() => { await page.waitForContentLoaded(); await page.waitToClick(selectors.routeIndex.addNewRouteButton); - let url = await page.expectURL('#!/route/create'); - - expect(url).toBe(true); + await page.waitForState('route.create'); }); it(`should attempt to create a new route but fail since employee has no access rights`, async() => { @@ -41,9 +39,7 @@ describe('Route create path', () => { it('should again click on the add new route button and open the creation form', async() => { await page.waitToClick(selectors.routeIndex.addNewRouteButton); - let url = await page.expectURL('#!/route/create'); - - expect(url).toBe(true); + await page.waitForState('route.create'); }); it(`should create a new route`, async() => { @@ -59,9 +55,7 @@ describe('Route create path', () => { }); it(`should confirm the redirection to the created route summary`, async() => { - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('route.card.summary'); }); }); }); diff --git a/e2e/paths/09-invoice-out/01_summary.spec.js b/e2e/paths/09-invoice-out/01_summary.spec.js index 126c745d3..728f0130a 100644 --- a/e2e/paths/09-invoice-out/01_summary.spec.js +++ b/e2e/paths/09-invoice-out/01_summary.spec.js @@ -17,9 +17,7 @@ describe('InvoiceOut summary path', () => { }); it('should reach the summary section', async() => { - const result = await page.expectURL('/summary'); - - expect(result).toBe(true); + await page.waitForState('invoiceOut.card.summary'); }); it('should contain the company from which the invoice is emited', async() => { diff --git a/e2e/paths/09-invoice-out/02_descriptor.spec.js b/e2e/paths/09-invoice-out/02_descriptor.spec.js index 1290b9a88..ceb2175e2 100644 --- a/e2e/paths/09-invoice-out/02_descriptor.spec.js +++ b/e2e/paths/09-invoice-out/02_descriptor.spec.js @@ -20,9 +20,7 @@ describe('InvoiceOut descriptor path', () => { await page.waitToClick(selectors.ticketsIndex.openAdvancedSearchButton); await page.write(selectors.ticketsIndex.advancedSearchInvoiceOut, 'T2222222'); await page.waitToClick(selectors.ticketsIndex.advancedSearchButton); - let url = await page.expectURL('#!/ticket/3/summary'); - - expect(url).toEqual(true); + await page.waitForState('ticket.card.summary'); }); it('should navigate to the invoiceOut index', async() => { @@ -30,16 +28,12 @@ describe('InvoiceOut descriptor path', () => { await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.invoiceOutButton); await page.wait(selectors.invoiceOutIndex.topbarSearch); - let url = await page.expectURL('#!/invoice-out/index'); - - expect(url).toBe(true); + await page.waitForState('invoiceOut.index'); }); it(`should click on the search result to access to the invoiceOut summary`, async() => { await page.accessToSearchResult('T2222222'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('invoiceOut.card.summary'); }); it('should delete the invoiceOut using the descriptor more menu', async() => { @@ -52,9 +46,7 @@ describe('InvoiceOut descriptor path', () => { }); it('should have been relocated to the invoiceOut index', async() => { - let url = await page.expectURL('#!/invoice-out/index'); - - expect(url).toBe(true); + await page.waitForState('invoiceOut.index'); }); it(`should search for the deleted invouceOut to find no results`, async() => { @@ -70,13 +62,10 @@ describe('InvoiceOut descriptor path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.ticketsButton); - let url = await page.expectURL('#!/ticket/index'); - - expect(url).toBe(true); + await page.waitForState('ticket.index'); }); it('should search for tickets with an specific invoiceOut to find no results', async() => { - await page.waitFor(2000); await page.waitToClick(selectors.ticketsIndex.openAdvancedSearchButton); await page.write(selectors.ticketsIndex.advancedSearchInvoiceOut, 'T2222222'); await page.waitToClick(selectors.ticketsIndex.advancedSearchButton); @@ -91,16 +80,12 @@ describe('InvoiceOut descriptor path', () => { await page.waitToClick(selectors.globalItems.applicationsMenuButton); await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.invoiceOutButton); - let url = await page.expectURL('#!/invoice-out/index'); - - expect(url).toBe(true); + await page.waitForState('invoiceOut.index'); }); it(`should search and access to the invoiceOut summary`, async() => { await page.accessToSearchResult('T1111111'); - let url = await page.expectURL('/summary'); - - expect(url).toBe(true); + await page.waitForState('invoiceOut.card.summary'); }); it(`should check the invoiceOut is booked in the summary data`, async() => { diff --git a/e2e/paths/10-travel/01_thermograph.spec.js b/e2e/paths/10-travel/01_thermograph.spec.js index efa2295a6..67a62381a 100644 --- a/e2e/paths/10-travel/01_thermograph.spec.js +++ b/e2e/paths/10-travel/01_thermograph.spec.js @@ -18,16 +18,12 @@ describe('Travel thermograph path', () => { }); it('should reach the thermograph section', async() => { - const result = await page.expectURL('/thermograph/index'); - - expect(result).toBe(true); + await page.waitForState('travel.card.thermograph.index'); }); it('should click the add thermograph floating button', async() => { await page.waitToClick(selectors.travelThermograph.add); - const result = await page.expectURL('/thermograph/create'); - - expect(result).toBe(true); + await page.waitForState('travel.card.thermograph.create'); }); it('should select the thermograph and then the file to upload', async() => { diff --git a/e2e/paths/10-travel/02_basic_data_and_log.spec.js b/e2e/paths/10-travel/02_basic_data_and_log.spec.js index c6287a8a0..85c7231c8 100644 --- a/e2e/paths/10-travel/02_basic_data_and_log.spec.js +++ b/e2e/paths/10-travel/02_basic_data_and_log.spec.js @@ -18,9 +18,7 @@ describe('Travel basic data path', () => { }); it('should reach the thermograph section', async() => { - const result = await page.expectURL('/basic-data'); - - expect(result).toBe(true); + await page.waitForState('travel.card.basicData'); }); it('should set a wrong delivery date then receive an error on submit', async() => { @@ -92,9 +90,7 @@ describe('Travel basic data path', () => { it('should navigate to the travel logs', async() => { await page.accessToSection('travel.card.log'); - const result = await page.expectURL('/log'); - - expect(result).toBe(true); + await page.waitForState('travel.card.log'); }); it('should check the 1st log contains details from the changes made', async() => { diff --git a/e2e/paths/11-zone/01_basic-data.spec.js b/e2e/paths/11-zone/01_basic-data.spec.js index 41b3782aa..7044ab70c 100644 --- a/e2e/paths/11-zone/01_basic-data.spec.js +++ b/e2e/paths/11-zone/01_basic-data.spec.js @@ -18,9 +18,7 @@ describe('Zone basic data path', () => { }); it('should reach the basic data section', async() => { - let url = await page.expectURL('#!/zone/10/basic-data'); - - expect(url).toBe(true); + await page.waitForState('zone.card.basicData'); }); it('should edit de form and then save', async() => { diff --git a/e2e/paths/12-entry/01_summary.spec.js b/e2e/paths/12-entry/01_summary.spec.js index 39b12b840..e57654f94 100644 --- a/e2e/paths/12-entry/01_summary.spec.js +++ b/e2e/paths/12-entry/01_summary.spec.js @@ -17,9 +17,7 @@ describe('Entry summary path', () => { }); it('should reach the second entry summary section', async() => { - let url = await page.expectURL('#!/entry/2/summary'); - - expect(url).toBe(true); + await page.waitForState('entry.card.summary'); }); it(`should display details from the entry on the header`, async() => { diff --git a/e2e/paths/12-entry/02_descriptor.spec.js b/e2e/paths/12-entry/02_descriptor.spec.js index 8fa0d2a4f..699d00517 100644 --- a/e2e/paths/12-entry/02_descriptor.spec.js +++ b/e2e/paths/12-entry/02_descriptor.spec.js @@ -17,9 +17,7 @@ describe('Entry descriptor path', () => { }); it('should reach the second entry summary section', async() => { - let url = await page.expectURL('#!/entry/2/summary'); - - expect(url).toBe(true); + await page.waitForState('entry.card.summary'); }); it('should show some entry information', async() => { @@ -30,32 +28,22 @@ describe('Entry descriptor path', () => { it('should click the travels button to be redirected to the travels index filtered by the current agency', async() => { await page.waitToClick(selectors.entryDescriptor.travelsQuicklink); - const url = await page.expectURL('/travel/index'); - const filter = await page.expectURL('agencyFk'); - - expect(url).toBe(true); - expect(filter).toBe(true); + await page.expectURL('/travel/index'); + await page.expectURL('agencyFk'); }); it('should go back to the entry summary', async() => { await page.waitToClick(selectors.globalItems.homeButton); await page.selectModule('entry'); await page.accessToSearchResult('2'); - let url = await page.expectURL('#!/entry/2/summary'); - - expect(url).toBe(true); + await page.waitForState('entry.card.summary'); }); it('should click the entries button to be redirected to the entries index filtered by the current supplier', async() => { await page.waitToClick(selectors.entryDescriptor.entriesQuicklink); - const url = await page.expectURL('/entry/index'); - const supplierFilter = await page.expectURL('supplierFk'); - const toFilter = await page.expectURL('to'); - const fromFilter = await page.expectURL('from'); - - expect(url).toBe(true); - expect(supplierFilter).toBe(true); - expect(toFilter).toBe(true); - expect(fromFilter).toBe(true); + await page.expectURL('/entry/index'); + await page.expectURL('supplierFk'); + await page.expectURL('to'); + await page.expectURL('from'); }); }); From 3283f957bac2a67a15de462f4099cfa0296f1ec9 Mon Sep 17 00:00:00 2001 From: Carlos Jimenez Ruiz Date: Tue, 24 Mar 2020 16:51:21 +0100 Subject: [PATCH 12/15] corrected a typo --- e2e/paths/02-client/01_create_client.spec.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/e2e/paths/02-client/01_create_client.spec.js b/e2e/paths/02-client/01_create_client.spec.js index 29a27884f..0b8c96c16 100644 --- a/e2e/paths/02-client/01_create_client.spec.js +++ b/e2e/paths/02-client/01_create_client.spec.js @@ -102,7 +102,7 @@ describe('Client create path', async() => { await page.wait(selectors.globalItems.applicationsMenuVisible); await page.waitToClick(selectors.globalItems.clientsButton); await page.wait(selectors.clientsIndex.createClientButton); - await page.waitForState('lient.index'); + await page.waitForState('client.index'); }); it(`should search for the user Carol Danvers to confirm it exists`, async() => { From 12c2b577e683a6c36701f042e26d9a14cebeeaec Mon Sep 17 00:00:00 2001 From: Carlos Jimenez Ruiz Date: Tue, 24 Mar 2020 17:01:11 +0100 Subject: [PATCH 13/15] minor refactor --- modules/order/front/card/index.js | 2 +- modules/order/front/line/index.js | 7 +++---- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/modules/order/front/card/index.js b/modules/order/front/card/index.js index e79167761..80fa99d1d 100644 --- a/modules/order/front/card/index.js +++ b/modules/order/front/card/index.js @@ -47,7 +47,7 @@ class Controller extends ModuleCard { ] }; - this.$q.all([ + return this.$q.all([ this.$http.get(`Orders/${this.$params.id}`, {filter}) .then(res => this.order = res.data), this.$http.get(`Orders/${this.$params.id}/getTotal`) diff --git a/modules/order/front/line/index.js b/modules/order/front/line/index.js index 149251c87..9351c5df8 100644 --- a/modules/order/front/line/index.js +++ b/modules/order/front/line/index.js @@ -43,10 +43,9 @@ class Controller extends Section { rows: [row.id], actualOrderId: this.$params.id }; - return this.$http.post(`OrderRows/removes`, params).then(() => { - this.card.reload(); - this.vnApp.showSuccess(this.$t('Data saved!')); - }); + return this.$http.post(`OrderRows/removes`, params) + .then(() => this.card.reload()) + .then(() => this.vnApp.showSuccess(this.$t('Data saved!'))); } showDescriptor(event, itemFk) { From 8eb6590285ae9d592d624d3f0a54e8d84f91c3de Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Tue, 24 Mar 2020 17:27:21 +0100 Subject: [PATCH 14/15] E2E fixes --- e2e/helpers/extensions.js | 11 ++++++++-- e2e/helpers/puppeteer.js | 2 +- e2e/helpers/selectors.js | 1 - e2e/paths/04-item/13_request.spec.js | 5 ++--- modules/item/front/request/index.html | 7 +++--- modules/item/front/request/index.js | 27 ++++++++++++------------ modules/item/front/request/index.spec.js | 21 +++++++++--------- 7 files changed, 40 insertions(+), 34 deletions(-) diff --git a/e2e/helpers/extensions.js b/e2e/helpers/extensions.js index 1ff0119fd..a7f4cc42c 100644 --- a/e2e/helpers/extensions.js +++ b/e2e/helpers/extensions.js @@ -545,7 +545,7 @@ let actions = { return dialogs.length; }, response); - this.waitForFunction(firstCount => { + await this.waitForFunction(firstCount => { const dialogs = document.querySelectorAll('.vn-dialog'); return dialogs.length < firstCount; }, {}, firstCount); @@ -559,7 +559,14 @@ let actions = { export function extendPage(page) { for (let name in actions) { page[name] = async(...args) => { - return await actions[name].call(page, ...args); + try { + return await actions[name].apply(page, args); + } catch (err) { + let stringArgs = args + .map(i => typeof i == 'function' ? 'Function' : i) + .join(', '); + throw new Error(`.${name}(${stringArgs}): ${err.message}`); + } }; } diff --git a/e2e/helpers/puppeteer.js b/e2e/helpers/puppeteer.js index 1ea3c1c90..67f9da427 100644 --- a/e2e/helpers/puppeteer.js +++ b/e2e/helpers/puppeteer.js @@ -12,7 +12,7 @@ export async function getBrowser() { if (process.env.DEBUG) args.push('--auto-open-devtools-for-tabs'); - const headless = !process.env.E2E_SHOW; + const headless = !(process.env.E2E_SHOW || process.env.DEBUG); const browser = await Puppeteer.launch({ args, defaultViewport: null, diff --git a/e2e/helpers/selectors.js b/e2e/helpers/selectors.js index 88f7cb40d..5469c09df 100644 --- a/e2e/helpers/selectors.js +++ b/e2e/helpers/selectors.js @@ -260,7 +260,6 @@ export default { secondRequestDecline: 'vn-item-request vn-tbody > vn-tr:nth-child(1) vn-icon-button[icon="thumb_down"]', declineReason: 'vn-textarea[ng-model="$ctrl.denyObservation"]', acceptDeclineReason: 'button[response="accept"]', - }, itemBasicData: { basicDataButton: 'vn-left-menu a[ui-sref="item.card.basicData"]', diff --git a/e2e/paths/04-item/13_request.spec.js b/e2e/paths/04-item/13_request.spec.js index d6aecbb48..aa4a57bc0 100644 --- a/e2e/paths/04-item/13_request.spec.js +++ b/e2e/paths/04-item/13_request.spec.js @@ -38,9 +38,8 @@ describe('Item request path', () => { it('should now click on the second declain request icon then type the reason', async() => { await page.waitToClick(selectors.itemRequest.secondRequestDecline); - await page.write(selectors.itemRequest.declineReason, 'not quite as expected'); - await page.waitToClick(selectors.itemRequest.acceptDeclineReason); - await page.waitForContentLoaded(); + await page.write(selectors.itemRequest.declineReason, 'Not quite as expected'); + await page.respondToDialog('accept'); let status = await page.waitToGetProperty(selectors.itemRequest.firstRequestStatus, 'innerText'); expect(status).toContain('Denegada'); diff --git a/modules/item/front/request/index.html b/modules/item/front/request/index.html index 20da8946d..0516e7ff5 100644 --- a/modules/item/front/request/index.html +++ b/modules/item/front/request/index.html @@ -91,7 +91,7 @@ @@ -111,8 +111,9 @@ vn-id="itemDescriptor"> + vn-id="deny-dialog" + on-accept="$ctrl.onDenyAccept($data)" + on-close="$ctrl.onDenyClose()">
Specify the reasons to deny this request
diff --git a/modules/item/front/request/index.js b/modules/item/front/request/index.js index 3684a1911..51035c468 100644 --- a/modules/item/front/request/index.js +++ b/modules/item/front/request/index.js @@ -1,8 +1,8 @@ import ngModule from '../module'; -import Component from 'core/lib/component'; +import Section from 'salix/components/section'; import './style.scss'; -export default class Controller extends Component { +export default class Controller extends Section { constructor($element, $) { super($element, $); @@ -33,7 +33,7 @@ export default class Controller extends Component { getState(isOk) { if (isOk === null) return 'Nueva'; - else if (isOk === -1 || isOk) + else if (isOk) return 'Aceptada'; else return 'Denegada'; @@ -102,25 +102,26 @@ export default class Controller extends Component { delete this.denyRequestId; } - denyRequest(response) { - if (response !== 'accept') return; - + onDenyAccept(request) { let params = { observation: this.denyObservation }; - let query = `TicketRequests/${this.selectedRequest.id}/deny`; - this.$http.post(query, params).then(res => { - const request = res.data; - this.selectedRequest.isOk = request.isOk; - this.selectedRequest.attenderFk = request.attenderFk; - this.selectedRequest.response = request.response; + let query = `TicketRequests/${request.id}/deny`; + return this.$http.post(query, params).then(res => { + const newRequest = res.data; + request.isOk = newRequest.isOk; + request.attenderFk = newRequest.attenderFk; + request.response = newRequest.response; this.vnApp.showSuccess(this.$t('Data saved!')); - this.denyObservation = null; }); } + onDenyClose() { + this.denyObservation = null; + } + showTicketDescriptor(event, ticketFk) { this.$.ticketDescriptor.ticketFk = ticketFk; this.$.ticketDescriptor.parent = event.target; diff --git a/modules/item/front/request/index.spec.js b/modules/item/front/request/index.spec.js index aaaade566..c988627ea 100644 --- a/modules/item/front/request/index.spec.js +++ b/modules/item/front/request/index.spec.js @@ -84,7 +84,6 @@ describe('Item', () => { let request = {saleFk: 1, saleQuantity: 1}; jest.spyOn(controller.vnApp, 'showSuccess'); - $httpBackend.when('PATCH', `Sales/${request.saleFk}/`).respond(); $httpBackend.expect('PATCH', `Sales/${request.saleFk}/`).respond(); controller.changeQuantity(request); @@ -112,20 +111,20 @@ describe('Item', () => { }); }); - describe('denyRequest()', () => { - it(`should perform a query and call vnApp.showSuccess(), refresh(), hide() and set denyObservation to null in the controller`, () => { - jest.spyOn(controller.vnApp, 'showSuccess'); + describe('onDenyAccept()', () => { + it(`should deny the request`, () => { + const request = { + id: 1, + response: 'new' + }; - const request = {id: 1}; - const expectedResult = {isOk: false, attenderFk: 106, response: 'Denied!'}; - controller.selectedRequest = request; + const url = `TicketRequests/:id/deny`; + $httpBackend.expectRoute('POST', url).respond({response: 'denied'}); - $httpBackend.when('POST', `TicketRequests/${request.id}/deny`).respond(expectedResult); - $httpBackend.expect('POST', `TicketRequests/${request.id}/deny`).respond(expectedResult); - controller.denyRequest('accept'); + controller.onDenyAccept(request); $httpBackend.flush(); - expect(controller.vnApp.showSuccess).toHaveBeenCalledWith('Data saved!'); + expect(request.response).toBe('denied'); }); }); }); From dcdae825d273ea10d143624f6d07b7d8030ea87f Mon Sep 17 00:00:00 2001 From: Bernat Exposito Domenech Date: Wed, 25 Mar 2020 08:43:49 +0100 Subject: [PATCH 15/15] fixex pull request --- modules/worker/front/worker-log/index.html | 2 +- modules/worker/front/worker-log/index.js | 12 ++---------- 2 files changed, 3 insertions(+), 11 deletions(-) diff --git a/modules/worker/front/worker-log/index.html b/modules/worker/front/worker-log/index.html index b38a456cb..090dbf2e3 100644 --- a/modules/worker/front/worker-log/index.html +++ b/modules/worker/front/worker-log/index.html @@ -1 +1 @@ - \ No newline at end of file + \ No newline at end of file diff --git a/modules/worker/front/worker-log/index.js b/modules/worker/front/worker-log/index.js index bd1e987c9..1f1a4f2f8 100644 --- a/modules/worker/front/worker-log/index.js +++ b/modules/worker/front/worker-log/index.js @@ -1,15 +1,7 @@ import ngModule from '../module'; - -class Controller { - constructor($scope, $stateParams) { - this.$scope = $scope; - this.$stateParams = $stateParams; - } -} - -Controller.$inject = ['$scope', '$stateParams']; +import Section from 'salix/components/section'; ngModule.component('vnWorkerLog', { template: require('./index.html'), - controller: Controller, + controller: Section, });