From b4bed608aba47838e500db6ebf5ceb3d28a4f9df Mon Sep 17 00:00:00 2001 From: alexm Date: Wed, 9 Feb 2022 15:01:02 +0100 Subject: [PATCH 01/31] refactor(ticket): getMovable --- db/changes/10411-january/00-ticket_getMovable.sql | 2 +- .../ticket/front/basic-data/step-two/index.html | 15 +++++++++++++-- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/db/changes/10411-january/00-ticket_getMovable.sql b/db/changes/10411-january/00-ticket_getMovable.sql index 5f5b0a93a3..051a86a7df 100644 --- a/db/changes/10411-january/00-ticket_getMovable.sql +++ b/db/changes/10411-january/00-ticket_getMovable.sql @@ -17,7 +17,7 @@ BEGIN FROM ticket t WHERE t.id = vTicketFk; - CALL itemStock(vWarehouseFk, DATE_SUB(vDatedNew, INTERVAL 1 DAY), NULL); + CALL itemStock(vWarehouseFk, vDatedNew, NULL); CALL item_getMinacum(vWarehouseFk, vDatedNew, DATEDIFF(vDatedOld, vDatedNew), NULL); SELECT s.id, diff --git a/modules/ticket/front/basic-data/step-two/index.html b/modules/ticket/front/basic-data/step-two/index.html index 092c9e7462..af06a0f70b 100644 --- a/modules/ticket/front/basic-data/step-two/index.html +++ b/modules/ticket/front/basic-data/step-two/index.html @@ -18,7 +18,14 @@ - {{("000000"+sale.itemFk).slice(-6)}} + + + {{("000000"+sale.itemFk).slice(-6)}} + +
{{::sale.item.name}} @@ -83,5 +90,9 @@
- + + From 135aff27a4caef315760aa1208c8d58ae4a0d3d5 Mon Sep 17 00:00:00 2001 From: alexm Date: Thu, 10 Feb 2022 09:13:48 +0100 Subject: [PATCH 02/31] fix(getMovable): show correct movable --- db/changes/10411-january/00-ticket_getMovable.sql | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/db/changes/10411-january/00-ticket_getMovable.sql b/db/changes/10411-january/00-ticket_getMovable.sql index 051a86a7df..eb5c722c45 100644 --- a/db/changes/10411-january/00-ticket_getMovable.sql +++ b/db/changes/10411-january/00-ticket_getMovable.sql @@ -6,20 +6,23 @@ CREATE DEFINER=`root`@`%` PROCEDURE `vn`.`ticket_getMovable`(vTicketFk INT, vDat BEGIN /** * Cálcula el stock movible para los artículos de un ticket + * vDatedNew debe ser menor que vDatedOld, en los otros casos se + * asume que siempre es posible * * @param vTicketFk -> Ticket * @param vDatedNew -> Nueva fecha * @return Sales con Movible */ DECLARE vDatedOld DATETIME; - + SET vDatedNew = DATE_ADD(vDatedNew, INTERVAL 1 DAY); + SELECT t.shipped INTO vDatedOld FROM ticket t WHERE t.id = vTicketFk; - CALL itemStock(vWarehouseFk, vDatedNew, NULL); - CALL item_getMinacum(vWarehouseFk, vDatedNew, DATEDIFF(vDatedOld, vDatedNew), NULL); - + CALL itemStock(vWarehouseFk, vDatedNew, NULL); + CALL item_getMinacum(vWarehouseFk, vDatedNew, DATEDIFF(DATE_SUB(vDatedOld, INTERVAL 1 DAY), vDatedNew), NULL); + SELECT s.id, s.itemFk, s.quantity, From 4e5e6dcccad1c5c5dfb29dc01532d56a9c5316e1 Mon Sep 17 00:00:00 2001 From: alexm Date: Thu, 10 Feb 2022 10:15:43 +0100 Subject: [PATCH 03/31] fix(test): change movable expeted --- .../ticket/back/methods/ticket/specs/priceDifference.spec.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/modules/ticket/back/methods/ticket/specs/priceDifference.spec.js b/modules/ticket/back/methods/ticket/specs/priceDifference.spec.js index e9aa5030a1..d8c785baa2 100644 --- a/modules/ticket/back/methods/ticket/specs/priceDifference.spec.js +++ b/modules/ticket/back/methods/ticket/specs/priceDifference.spec.js @@ -86,8 +86,8 @@ describe('sale priceDifference()', () => { const firstItem = result.items[0]; const secondtItem = result.items[1]; - expect(firstItem.movable).toEqual(440); - expect(secondtItem.movable).toEqual(1980); + expect(firstItem.movable).toEqual(410); + expect(secondtItem.movable).toEqual(1870); await tx.rollback(); } catch (e) { From ac0e55107a6c4c283a75516bc3ec357971538208 Mon Sep 17 00:00:00 2001 From: carlosjr Date: Tue, 15 Feb 2022 12:59:57 +0100 Subject: [PATCH 04/31] 3595 feat(toggleHidden): itemWaste now can hide panels --- modules/item/front/waste/index/index.html | 28 +++++++---- modules/item/front/waste/index/index.js | 29 ++++++++++- modules/item/front/waste/index/index.spec.js | 53 ++++++++++++++++++++ modules/item/front/waste/index/style.scss | 37 +++++++++----- 4 files changed, 123 insertions(+), 24 deletions(-) create mode 100644 modules/item/front/waste/index/index.spec.js diff --git a/modules/item/front/waste/index/index.html b/modules/item/front/waste/index/index.html index 7ad985ea8b..c80733e9e0 100644 --- a/modules/item/front/waste/index/index.html +++ b/modules/item/front/waste/index/index.html @@ -3,13 +3,21 @@ url="Items/getWasteByWorker" data="details"> - - -
- -
{{detail.buyer}}
-
+
+ +
{{detail.buyer}}
+ + + + +
+ @@ -21,7 +29,7 @@ + ui-sref="item.waste.detail({buyer: waste.buyer, family: waste.family})"> {{::waste.family}} {{::(waste.percentage / 100) | percentage: 2}} {{::waste.dwindle | currency: 'EUR'}} @@ -29,6 +37,6 @@ -
- - + +
+
\ No newline at end of file diff --git a/modules/item/front/waste/index/index.js b/modules/item/front/waste/index/index.js index 15e6b063f6..b11f54b080 100644 --- a/modules/item/front/waste/index/index.js +++ b/modules/item/front/waste/index/index.js @@ -2,7 +2,34 @@ import ngModule from '../../module'; import Section from 'salix/components/section'; import './style.scss'; +export default class Controller extends Section { + constructor($element, $) { + super($element, $); + + this.getWasteConfig(); + } + + getWasteConfig() { + return this.wasteConfig = JSON.parse(localStorage.getItem('wasteConfig')) || {}; + } + + setWasteConfig() { + localStorage.setItem('wasteConfig', JSON.stringify(this.wasteConfig)); + } + + toggleHidePanel(detail) { + if (!this.wasteConfig[detail.buyer]) { + this.wasteConfig[detail.buyer] = { + hidden: true + }; + } else + this.wasteConfig[detail.buyer].hidden = !this.wasteConfig[detail.buyer].hidden; + + this.setWasteConfig(); + } +} + ngModule.vnComponent('vnItemWasteIndex', { template: require('./index.html'), - controller: Section + controller: Controller }); diff --git a/modules/item/front/waste/index/index.spec.js b/modules/item/front/waste/index/index.spec.js new file mode 100644 index 0000000000..575e773bd2 --- /dev/null +++ b/modules/item/front/waste/index/index.spec.js @@ -0,0 +1,53 @@ +import './index.js'; +import crudModel from 'core/mocks/crud-model'; + +fdescribe('Item', () => { + describe('Component vnItemWasteIndex', () => { + let $scope; + let controller; + + beforeEach(ngModule('item')); + + beforeEach(inject(($componentController, $rootScope) => { + $scope = $rootScope.$new(); + $scope.model = crudModel; + const $element = angular.element(''); + controller = $componentController('vnItemWasteIndex', {$element, $scope}); + })); + + describe('getWasteConfig / setWasteConfig', () => { + it('should return the local storage wasteConfig', () => { + const result = controller.getWasteConfig(); + + expect(result).toEqual({}); + }); + + it('should set and return the local storage wasteConfig', () => { + controller.wasteConfig = {salesPerson: {hidden: true}}; + controller.setWasteConfig(); + + const result = controller.getWasteConfig(); + + expect(result).toEqual(controller.wasteConfig); + }); + }); + + describe('toggleHidePanel()', () => { + it('should make details hidden by default', () => { + controller.wasteConfig = {}; + + controller.toggleHidePanel({buyer: 'salesPerson'}); + + expect(controller.wasteConfig.salesPerson.hidden).toEqual(true); + }); + + it('should toggle hidden false', () => { + controller.wasteConfig = {salesPerson: {hidden: true}}; + + controller.toggleHidePanel({buyer: 'salesPerson'}); + + expect(controller.wasteConfig.salesPerson.hidden).toEqual(false); + }); + }); + }); +}); diff --git a/modules/item/front/waste/index/style.scss b/modules/item/front/waste/index/style.scss index faac461393..8b44cb6f17 100644 --- a/modules/item/front/waste/index/style.scss +++ b/modules/item/front/waste/index/style.scss @@ -1,21 +1,24 @@ @import "variables"; +@import "effects"; vn-item-waste-index, vn-item-waste-detail { .header { - margin-bottom: 16px; - text-transform: uppercase; - font-size: 1.25rem; - line-height: 1; - padding: 7px; - padding-bottom: 7px; - padding-bottom: 4px; - font-weight: lighter; - background-color: $color-bg; - border-bottom: 1px solid #f7931e; - white-space: nowrap; - overflow: hidden; - text-overflow: ellipsis; + padding: 12px 0 5px 0; + color: gray; + font-size: 1.2rem; + border-bottom: $border; + margin-bottom: 10px; + + & > vn-none > vn-icon { + @extend %clickable-light; + color: $color-button; + font-size: 1.4rem; + } + + vn-none > .arrow { + transition: transform 200ms; + } } vn-table vn-th.waste-family, @@ -23,4 +26,12 @@ vn-item-waste-detail { max-width: 64px; width: 64px } + .hidden { + display: none; + + } + .header > vn-none > .arrow.hidden { + display: block; + transform: rotate(180deg); + } } \ No newline at end of file From 401174b27a69ae0d461d735801fdb4e7866e7326 Mon Sep 17 00:00:00 2001 From: carlosjr Date: Tue, 15 Feb 2022 13:46:25 +0100 Subject: [PATCH 05/31] removed focus on describe --- modules/item/front/waste/index/index.spec.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/item/front/waste/index/index.spec.js b/modules/item/front/waste/index/index.spec.js index 575e773bd2..fd7332f686 100644 --- a/modules/item/front/waste/index/index.spec.js +++ b/modules/item/front/waste/index/index.spec.js @@ -1,7 +1,7 @@ import './index.js'; import crudModel from 'core/mocks/crud-model'; -fdescribe('Item', () => { +describe('Item', () => { describe('Component vnItemWasteIndex', () => { let $scope; let controller; From 651c92698fd193bc5f40a4b9d812d283aceb5bc4 Mon Sep 17 00:00:00 2001 From: alexm Date: Tue, 15 Feb 2022 16:48:37 +0100 Subject: [PATCH 06/31] feat(docuware): start download docuware --- back/methods/docuware/download.js | 88 +++++++++++++++++++ back/model-config.json | 3 + back/models/docuware.js | 3 + back/models/docuware.json | 38 ++++++++ .../10420-valentines/00-aclDocuware.sql | 3 + db/changes/10420-valentines/00-docuware.sql | 11 +++ .../10420-valentines/00-docuwareConfig.sql | 9 ++ .../back/methods/invoiceOut/docuware.js | 65 ++++++++++++++ modules/invoiceOut/back/models/invoice-out.js | 1 + .../front/descriptor-menu/index.html | 5 ++ .../invoiceOut/front/descriptor-menu/index.js | 13 +++ 11 files changed, 239 insertions(+) create mode 100644 back/methods/docuware/download.js create mode 100644 back/models/docuware.js create mode 100644 back/models/docuware.json create mode 100644 db/changes/10420-valentines/00-aclDocuware.sql create mode 100644 db/changes/10420-valentines/00-docuware.sql create mode 100644 db/changes/10420-valentines/00-docuwareConfig.sql create mode 100644 modules/invoiceOut/back/methods/invoiceOut/docuware.js diff --git a/back/methods/docuware/download.js b/back/methods/docuware/download.js new file mode 100644 index 0000000000..01e552d2d1 --- /dev/null +++ b/back/methods/docuware/download.js @@ -0,0 +1,88 @@ +const got = require('got'); +const {createWriteStream} = require('fs'); +const UserError = require('vn-loopback/util/user-error'); + +module.exports = Self => { + Self.remoteMethodCtx('download', { + description: 'Download an invoice PDF', + accessType: 'READ', + accepts: [ + { + arg: 'ticketId', + type: 'number', + description: 'The invoiceable ticket id' + }, + ], + returns: { + type: 'object', + root: true + }, + http: { + path: `/download`, + verb: 'POST' + } + }); + + Self.download = async function(ctx, ticketId) { + // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; + // hay que crear tambien una busqueda por cada fileCabinet + // columnas necesarias. seccion, fileCabinet, DBName, dialog + const models = Self.app.models; + const [docuwareConfig] = await Self.rawSql(`SELECT * FROM vn.docuwareConfig;`); + const docuwareInfo = await models.Docuware.findOne({ + where: { + name: 'deliveryClient', + dialogName: 'findTicket' + } + }); + console.log(docuwareConfig, docuwareInfo); + + const docuwareUrl = docuwareConfig.url; + const cookie = docuwareConfig.token; + const fileCabinetName = docuwareInfo.fileCabinetName; + const find = docuwareInfo.find; + + // get fileCabinetId + const options = { + 'headers': { + 'Accept': 'application/json', + 'Content-Type': 'application/json', + 'Cookie': cookie + } + }; + + const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options).json(); + const fileCabinetId = fileCabinetResponse.FileCabinet.find(dialogs => dialogs.Name === fileCabinetName).Id; + + // get dialogs + const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options).json(); + console.log(dialogResponse); + const dialogId = dialogResponse.Dialog.find(dialogs => dialogs.DisplayName === 'find').Id; + + console.log(fileCabinetId, dialogId); + /* + // get DocuwareID + const docuwareOptions = { + 'headers': { + 'Accept': 'application/json', + 'Content-Type': 'application/json', + 'Cookie': cookie + }, + 'body': JSON.stringify({'Condition': [{DBName: find, Value: [ticketId]}]}) + }; + const response = await got.post(`${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, docuwareOptions); + const docuwareId = JSON.parse(response.body).Items[0].Id; + + // download file + const downloadUrl = `${docuwareUrl}/FileCabinets/${fileCabinetId}/Documents/${docuwareId}/FileDownload?targetFileType=Auto&keepAnnotations=false`; + const downloadOptions = { + 'headers': { + 'Cookie': cookie + } + }; + + const file = await got.stream(downloadUrl, downloadOptions).pipe(createWriteStream(`${ticketId}_${docuwareId}.pdf`)); + + // return [file, 'application/pdf', `filename="${ticketId}_${docuwareId}.pdf"`];*/ + }; +}; diff --git a/back/model-config.json b/back/model-config.json index 8ad15a16a7..7be2174e6a 100644 --- a/back/model-config.json +++ b/back/model-config.json @@ -44,6 +44,9 @@ "DmsType": { "dataSource": "vn" }, + "Docuware": { + "dataSource": "vn" + }, "EmailUser": { "dataSource": "vn" }, diff --git a/back/models/docuware.js b/back/models/docuware.js new file mode 100644 index 0000000000..8a6b0cd935 --- /dev/null +++ b/back/models/docuware.js @@ -0,0 +1,3 @@ +module.exports = Self => { + require('../methods/docuware/download')(Self); +}; diff --git a/back/models/docuware.json b/back/models/docuware.json new file mode 100644 index 0000000000..f853970722 --- /dev/null +++ b/back/models/docuware.json @@ -0,0 +1,38 @@ +{ + "name": "Docuware", + "description": "Docuware sections", + "base": "VnModel", + "options": { + "mysql": { + "table": "docuware" + } + }, + "properties": { + "id": { + "type": "number", + "id": true, + "description": "Identifier" + }, + "name": { + "type": "string" + }, + "fileCabinetName": { + "type": "string" + }, + "dialogName": { + "type": "string" + }, + "find": { + "type": "string" + } + }, + "acls": [ + { + "property": "*", + "accessType": "*", + "principalType": "ROLE", + "principalId": "$everyone", + "permission": "ALLOW" + } + ] +} \ No newline at end of file diff --git a/db/changes/10420-valentines/00-aclDocuware.sql b/db/changes/10420-valentines/00-aclDocuware.sql new file mode 100644 index 0000000000..21ed66c4c7 --- /dev/null +++ b/db/changes/10420-valentines/00-aclDocuware.sql @@ -0,0 +1,3 @@ +INSERT INTO salix.ACL +(model, property, accessType, permission, principalType, principalId) +VALUES('Docuware', '*', '*', 'ALLOW', 'ROLE', 'employee'); \ No newline at end of file diff --git a/db/changes/10420-valentines/00-docuware.sql b/db/changes/10420-valentines/00-docuware.sql new file mode 100644 index 0000000000..dd915ddcdc --- /dev/null +++ b/db/changes/10420-valentines/00-docuware.sql @@ -0,0 +1,11 @@ +CREATE TABLE `vn`.`docuware` ( + `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY, + `name` varchar(50) NULL, + `fileCabinetName` varchar(50) NULL, + `dialogName` varchar(255) DEFAULT NULL, + `find` varchar(50) DEFAULT NULL +); + +INSERT INTO `vn`.`docuware` +(name, fileCabinetName, dialogName , find) +VALUES('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); diff --git a/db/changes/10420-valentines/00-docuwareConfig.sql b/db/changes/10420-valentines/00-docuwareConfig.sql new file mode 100644 index 0000000000..0ef190cb79 --- /dev/null +++ b/db/changes/10420-valentines/00-docuwareConfig.sql @@ -0,0 +1,9 @@ +CREATE TABLE `vn`.`docuwareConfig` ( + `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY, + `url` varchar(75) NULL, + `token` varchar(1000) DEFAULT NULL +); + +INSERT INTO `vn`.`docuwareConfig` +(url, token) +VALUES('https://verdnatura.docuware.cloud/docuware/platform/', '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'); diff --git a/modules/invoiceOut/back/methods/invoiceOut/docuware.js b/modules/invoiceOut/back/methods/invoiceOut/docuware.js new file mode 100644 index 0000000000..aa58aaed17 --- /dev/null +++ b/modules/invoiceOut/back/methods/invoiceOut/docuware.js @@ -0,0 +1,65 @@ +const got = require('got'); +const {createWriteStream} = require('fs'); +const UserError = require('vn-loopback/util/user-error'); + +module.exports = Self => { + Self.remoteMethodCtx('docuware', { + description: 'Download an invoice PDF', + accessType: 'READ', + accepts: [ + { + arg: 'ticketId', + type: 'number', + description: 'The invoiceable ticket id' + }, + ], + returns: { + type: 'object', + root: true + }, + http: { + path: `/docuware`, + verb: 'POST' + } + }); + + Self.docuware = async function(ctx, ticketId) { + // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; + // hay que crear tambien una busqueda por cada fileCabinet + // columnas necesarias. seccion, fileCabinet, DBName, dialog + const models = Self.app.models; + const docuwareInfo = await models.Docuware.findOne({ + where: { + name: 'albaran' + } + }); + console.log(docuwareInfo); + const fileCabinet = docuwareInfo.fileCabinet; + const find = docuwareInfo.find; + const dialog = docuwareInfo.dialog; + const docuwareUrl = `https://verdnatura.docuware.cloud/docuware/platform/FileCabinets/${fileCabinet}`; + const cookie = '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'; + + // get DocuwareID + const dialogOptions = { + 'headers': { + 'Accept': 'application/json', + 'Content-Type': 'application/json', + 'Cookie': cookie + }, + 'body': JSON.stringify({'Condition': [{DBName: find, Value: [ticketId]}]}) + }; + const response = await got.post(`${docuwareUrl}/Query/DialogExpression?dialogId=${dialog}`, dialogOptions); + const docuwareId = JSON.parse(response.body).Items[0].Id; + + // download file + const downloadUrl = `${docuwareUrl}/Documents/${docuwareId}/FileDownload?targetFileType=Auto&keepAnnotations=false`; + const downloadOptions = { + 'headers': { + 'Cookie': cookie + } + }; + + await got.stream(downloadUrl, downloadOptions).pipe(createWriteStream(`${ticketId}_${docuwareId}.pdf`)); + }; +}; diff --git a/modules/invoiceOut/back/models/invoice-out.js b/modules/invoiceOut/back/models/invoice-out.js index 3b2822ada1..3da5aedc69 100644 --- a/modules/invoiceOut/back/models/invoice-out.js +++ b/modules/invoiceOut/back/models/invoice-out.js @@ -3,6 +3,7 @@ module.exports = Self => { require('../methods/invoiceOut/summary')(Self); require('../methods/invoiceOut/getTickets')(Self); require('../methods/invoiceOut/download')(Self); + require('../methods/invoiceOut/docuware')(Self); require('../methods/invoiceOut/delete')(Self); require('../methods/invoiceOut/book')(Self); require('../methods/invoiceOut/createPdf')(Self); diff --git a/modules/invoiceOut/front/descriptor-menu/index.html b/modules/invoiceOut/front/descriptor-menu/index.html index 3b30f891cd..070da18e12 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.html +++ b/modules/invoiceOut/front/descriptor-menu/index.html @@ -20,6 +20,11 @@ translate> Show as PDF + + Show as DOCUWARE + diff --git a/modules/invoiceOut/front/descriptor-menu/index.js b/modules/invoiceOut/front/descriptor-menu/index.js index 7738845f97..f6855795a5 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.js +++ b/modules/invoiceOut/front/descriptor-menu/index.js @@ -88,6 +88,19 @@ class Controller extends Section { }); } + downloadDocuware() { + const options = { + ticketId: 3367050 + }; + + return this.$http.post(`Docuwares/download`, options) + .then(() => { + const snackbarMessage = this.$t( + `The invoice PDF document has been downloaded`); + this.vnApp.showSuccess(snackbarMessage); + }); + } + sendPdfInvoice($data) { if (!$data.email) return this.vnApp.showError(this.$t(`The email can't be empty`)); From 3aeb2adb56bc5e4db554f02001748c9b9aacfc8f Mon Sep 17 00:00:00 2001 From: alexm Date: Wed, 16 Feb 2022 14:57:47 +0100 Subject: [PATCH 07/31] feat(ticket): docuware pdf --- back/methods/docuware/checkFile.js | 80 +++++++++++ back/methods/docuware/download.js | 104 ++++++++++---- back/methods/docuware/specs/checkFile.spec.js | 129 ++++++++++++++++++ back/methods/docuware/specs/download.spec.js | 28 ++++ back/model-config.json | 6 + back/models/docuware-config.json | 32 +++++ back/models/docuware-container.json | 10 ++ back/models/docuware.js | 1 + db/changes/10420-valentines/00-docuware.sql | 6 +- .../10420-valentines/00-docuwareConfig.sql | 6 +- db/dump/fixtures.sql | 8 ++ loopback/server/datasources.json | 11 ++ .../back/methods/invoiceOut/docuware.js | 65 --------- modules/invoiceOut/back/models/invoice-out.js | 1 - .../ticket/front/descriptor-menu/index.html | 12 +- modules/ticket/front/descriptor-menu/index.js | 8 ++ .../front/descriptor-menu/locale/es.yml | 4 +- 17 files changed, 408 insertions(+), 103 deletions(-) create mode 100644 back/methods/docuware/checkFile.js create mode 100644 back/methods/docuware/specs/checkFile.spec.js create mode 100644 back/methods/docuware/specs/download.spec.js create mode 100644 back/models/docuware-config.json create mode 100644 back/models/docuware-container.json delete mode 100644 modules/invoiceOut/back/methods/invoiceOut/docuware.js diff --git a/back/methods/docuware/checkFile.js b/back/methods/docuware/checkFile.js new file mode 100644 index 0000000000..7dc1993f04 --- /dev/null +++ b/back/methods/docuware/checkFile.js @@ -0,0 +1,80 @@ +const got = require('got'); +const UserError = require('vn-loopback/util/user-error'); + +module.exports = Self => { + Self.remoteMethodCtx('checkFile', { + description: 'Download an docuware PDF', + accessType: 'READ', + accepts: [ + { + arg: 'id', + type: 'String', + description: 'The invoice id', + http: {source: 'path'} + } + ], + returns: { + type: 'boolean', + root: true + }, + http: { + path: `/:id/checkFile`, + verb: 'GET' + } + }); + + Self.checkFile = async function(ctx, id) { + // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; + // hay que crear tambien una busqueda por cada fileCabinet + // columnas necesarias. seccion, fileCabinet, DBName, dialog + + const models = Self.app.models; + const docuwareConfig = await models.DocuwareConfig.findOne(); + const docuwareInfo = await models.Docuware.findOne({ + where: { + name: 'deliveryClient', + dialogName: 'findTicket' + } + }); + + const docuwareUrl = docuwareConfig.url; + const cookie = docuwareConfig.token; + const fileCabinetName = docuwareInfo.fileCabinetName; + const find = docuwareInfo.find; + + const options = { + 'headers': { + 'Accept': 'application/json', + 'Content-Type': 'application/json', + 'Cookie': cookie + } + }; + // get fileCabinetId + const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options).json(); + const fileCabinetId = fileCabinetResponse.FileCabinet.find(dialogs => dialogs.Name === fileCabinetName).Id; + + // get dialog + const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options).json(); + const dialogId = dialogResponse.Dialog.find(dialogs => dialogs.DisplayName === 'find').Id; + + // get docuwareID + const docuwareOptions = { + 'headers': { + 'Accept': 'application/json', + 'Content-Type': 'application/json', + 'Cookie': cookie + }, + 'body': JSON.stringify({'Condition': [{DBName: find, Value: [id]}]}) + }; + const response = await got.post( + `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, + docuwareOptions + ); + try { + JSON.parse(response.body).Items[0].Id; + return true; + } catch (error) { + return false; + } + }; +}; diff --git a/back/methods/docuware/download.js b/back/methods/docuware/download.js index 01e552d2d1..a2a95fcd18 100644 --- a/back/methods/docuware/download.js +++ b/back/methods/docuware/download.js @@ -1,48 +1,65 @@ const got = require('got'); -const {createWriteStream} = require('fs'); +const fs = require('fs-extra'); +const path = require('path'); const UserError = require('vn-loopback/util/user-error'); +const {promisify} = require('util'); +const nodeStream = require('stream'); module.exports = Self => { Self.remoteMethodCtx('download', { - description: 'Download an invoice PDF', + description: 'Download an docuware PDF', accessType: 'READ', accepts: [ { - arg: 'ticketId', + arg: 'id', type: 'number', - description: 'The invoiceable ticket id' - }, + description: 'The ticket id', + http: {source: 'path'} + } + ], + returns: [ + { + arg: 'body', + type: 'file', + root: true + }, { + arg: 'Content-Type', + type: 'String', + http: {target: 'header'} + }, { + arg: 'Content-Disposition', + type: 'String', + http: {target: 'header'} + } ], - returns: { - type: 'object', - root: true - }, http: { - path: `/download`, - verb: 'POST' + path: `/:id/download`, + verb: 'GET' } }); - Self.download = async function(ctx, ticketId) { + Self.download = async function(ctx, id) { // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; // hay que crear tambien una busqueda por cada fileCabinet // columnas necesarias. seccion, fileCabinet, DBName, dialog + /* const myUserId = ctx.req.accessToken.userId; + if (!myUserId) + throw new UserError(`You don't have enough privileges`);*/ + const models = Self.app.models; - const [docuwareConfig] = await Self.rawSql(`SELECT * FROM vn.docuwareConfig;`); + const docuwareConfig = await models.DocuwareConfig.findOne(); const docuwareInfo = await models.Docuware.findOne({ where: { name: 'deliveryClient', dialogName: 'findTicket' } }); - console.log(docuwareConfig, docuwareInfo); const docuwareUrl = docuwareConfig.url; const cookie = docuwareConfig.token; const fileCabinetName = docuwareInfo.fileCabinetName; const find = docuwareInfo.find; - // get fileCabinetId const options = { 'headers': { 'Accept': 'application/json', @@ -50,27 +67,27 @@ module.exports = Self => { 'Cookie': cookie } }; - + // get fileCabinetId const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options).json(); const fileCabinetId = fileCabinetResponse.FileCabinet.find(dialogs => dialogs.Name === fileCabinetName).Id; - // get dialogs + // get dialog const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options).json(); - console.log(dialogResponse); const dialogId = dialogResponse.Dialog.find(dialogs => dialogs.DisplayName === 'find').Id; - console.log(fileCabinetId, dialogId); - /* - // get DocuwareID + // get docuwareID const docuwareOptions = { 'headers': { 'Accept': 'application/json', 'Content-Type': 'application/json', 'Cookie': cookie }, - 'body': JSON.stringify({'Condition': [{DBName: find, Value: [ticketId]}]}) + 'body': JSON.stringify({'Condition': [{DBName: find, Value: [0]}]}) }; - const response = await got.post(`${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, docuwareOptions); + const response = await got.post( + `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, + docuwareOptions + ); const docuwareId = JSON.parse(response.body).Items[0].Id; // download file @@ -81,8 +98,45 @@ module.exports = Self => { } }; - const file = await got.stream(downloadUrl, downloadOptions).pipe(createWriteStream(`${ticketId}_${docuwareId}.pdf`)); + try { + // save file + const ticket = await models.Ticket.findById(id); - // return [file, 'application/pdf', `filename="${ticketId}_${docuwareId}.pdf"`];*/ + const shipped = ticket.shipped; + const year = shipped.getFullYear().toString(); + const month = (shipped.getMonth() + 1).toString(); + const day = shipped.getDate().toString(); + const fileName = `${year}${id}.pdf`; + + const container = await models.DocuwareContainer.container(year); + const rootPath = container.client.root; + const src = path.join(rootPath, year, month, day); + const fileSrc = path.join(src, fileName); + + await fs.mkdir(src, {recursive: true}); + + const pipeline = promisify(nodeStream.pipeline); + await pipeline( + got.stream(downloadUrl, downloadOptions), + fs.createWriteStream(fileSrc) + ); + + // open file + const file = { + path: fileSrc, + contentType: 'application/pdf', + name: fileName + }; + + await fs.access(file.path); + let stream = fs.createReadStream(file.path); + + return [stream, file.contentType, `filename="${file.name}"`]; + } catch (error) { + if (error.code === 'ENOENT') + throw new UserError('The DOCUWARE PDF document does not exists'); + + throw error; + } }; }; diff --git a/back/methods/docuware/specs/checkFile.spec.js b/back/methods/docuware/specs/checkFile.spec.js new file mode 100644 index 0000000000..7cb2ae6f92 --- /dev/null +++ b/back/methods/docuware/specs/checkFile.spec.js @@ -0,0 +1,129 @@ +const app = require('vn-loopback/server/server'); + +describe('image upload()', () => { + describe('as buyer', () => { + const buyerId = 35; + const workerId = 1106; + const itemId = 4; + + it('should try to upload a file for the collection "catalog" and throw a privileges error', async() => { + const ctx = {req: {accessToken: {userId: buyerId}}, + args: { + id: workerId, + collection: 'user' + } + }; + + let error; + try { + await app.models.Image.upload(ctx); + } catch (err) { + error = err; + } + + expect(error.message).toEqual(`You don't have enough privileges`); + }); + + it('should call to the TempContainer upload method for the collection "catalog"', async() => { + const containerModel = app.models.TempContainer; + spyOn(containerModel, 'upload'); + + const ctx = {req: {accessToken: {userId: buyerId}}, + args: { + id: itemId, + collection: 'catalog' + } + }; + + try { + await app.models.Image.upload(ctx); + } catch (err) { } + + expect(containerModel.upload).toHaveBeenCalled(); + }); + }); + + describe('as marketing', () => { + const marketingId = 51; + const workerId = 1106; + const itemId = 4; + + it('should be able to call to the TempContainer upload method for the collection "user"', async() => { + const containerModel = app.models.TempContainer; + spyOn(containerModel, 'upload'); + + const ctx = {req: {accessToken: {userId: marketingId}}, + args: { + id: workerId, + collection: 'user' + } + }; + + try { + await app.models.Image.upload(ctx); + } catch (err) { } + + expect(containerModel.upload).toHaveBeenCalled(); + }); + + it('should be able to call to the TempContainer upload method for the collection "catalog"', async() => { + const containerModel = app.models.TempContainer; + spyOn(containerModel, 'upload'); + + const ctx = {req: {accessToken: {userId: marketingId}}, + args: { + id: itemId, + collection: 'catalog' + } + }; + + try { + await app.models.Image.upload(ctx); + } catch (err) { } + + expect(containerModel.upload).toHaveBeenCalled(); + }); + }); + + describe('as hhrr', () => { + const hhrrId = 37; + const workerId = 1106; + const itemId = 4; + + it('should upload a file for the collection "user" and call to the TempContainer upload method', async() => { + const containerModel = app.models.TempContainer; + spyOn(containerModel, 'upload'); + + const ctx = {req: {accessToken: {userId: hhrrId}}, + args: { + id: itemId, + collection: 'user' + } + }; + + try { + await app.models.Image.upload(ctx); + } catch (err) { } + + expect(containerModel.upload).toHaveBeenCalled(); + }); + + it('should try to upload a file for the collection "catalog" and throw a privilege error', async() => { + const ctx = {req: {accessToken: {userId: hhrrId}}, + args: { + id: workerId, + collection: 'catalog' + } + }; + + let error; + try { + await app.models.Image.upload(ctx); + } catch (err) { + error = err; + } + + expect(error.message).toEqual(`You don't have enough privileges`); + }); + }); +}); diff --git a/back/methods/docuware/specs/download.spec.js b/back/methods/docuware/specs/download.spec.js new file mode 100644 index 0000000000..4bdf800b48 --- /dev/null +++ b/back/methods/docuware/specs/download.spec.js @@ -0,0 +1,28 @@ +const models = require('vn-loopback/server/server').models; +const fs = require('fs-extra'); + +describe('image download()', () => { + const userId = 9; + const invoiceId = 1; + const ctx = { + req: { + + accessToken: {userId: userId}, + headers: {origin: 'http://localhost:5000'}, + } + }; + + it('should return the downloaded file name', async() => { + spyOn(models.DocuwareContainer, 'container').and.returnValue({ + client: {root: '/path'} + }); + spyOn(fs, 'createReadStream').and.returnValue(new Promise(resolve => resolve('streamObject'))); + spyOn(fs, 'access').and.returnValue(true); + spyOn(models.InvoiceOut, 'createPdf').and.returnValue(new Promise(resolve => resolve(true))); + + const result = await models.InvoiceOut.download(ctx, invoiceId); + + expect(result[1]).toEqual('application/pdf'); + expect(result[2]).toMatch(/filename="\d{4}T1111111.pdf"/); + }); +}); diff --git a/back/model-config.json b/back/model-config.json index 7be2174e6a..f1b6623546 100644 --- a/back/model-config.json +++ b/back/model-config.json @@ -47,6 +47,12 @@ "Docuware": { "dataSource": "vn" }, + "DocuwareConfig": { + "dataSource": "vn" + }, + "DocuwareContainer": { + "dataSource": "docuwareStorage" + }, "EmailUser": { "dataSource": "vn" }, diff --git a/back/models/docuware-config.json b/back/models/docuware-config.json new file mode 100644 index 0000000000..8ca76d8bad --- /dev/null +++ b/back/models/docuware-config.json @@ -0,0 +1,32 @@ +{ + "name": "DocuwareConfig", + "description": "Docuware config", + "base": "VnModel", + "options": { + "mysql": { + "table": "docuwareConfig" + } + }, + "properties": { + "id": { + "type": "number", + "id": true, + "description": "Identifier" + }, + "url": { + "type": "string" + }, + "token": { + "type": "string" + } + }, + "acls": [ + { + "property": "*", + "accessType": "*", + "principalType": "ROLE", + "principalId": "$everyone", + "permission": "ALLOW" + } + ] +} \ No newline at end of file diff --git a/back/models/docuware-container.json b/back/models/docuware-container.json new file mode 100644 index 0000000000..8180695c18 --- /dev/null +++ b/back/models/docuware-container.json @@ -0,0 +1,10 @@ +{ + "name": "DocuwareContainer", + "base": "Container", + "acls": [{ + "accessType": "READ", + "principalType": "ROLE", + "principalId": "$everyone", + "permission": "ALLOW" + }] +} \ No newline at end of file diff --git a/back/models/docuware.js b/back/models/docuware.js index 8a6b0cd935..8fd8065edb 100644 --- a/back/models/docuware.js +++ b/back/models/docuware.js @@ -1,3 +1,4 @@ module.exports = Self => { require('../methods/docuware/download')(Self); + require('../methods/docuware/checkFile')(Self); }; diff --git a/db/changes/10420-valentines/00-docuware.sql b/db/changes/10420-valentines/00-docuware.sql index dd915ddcdc..ca4b0a1142 100644 --- a/db/changes/10420-valentines/00-docuware.sql +++ b/db/changes/10420-valentines/00-docuware.sql @@ -6,6 +6,6 @@ CREATE TABLE `vn`.`docuware` ( `find` varchar(50) DEFAULT NULL ); -INSERT INTO `vn`.`docuware` -(name, fileCabinetName, dialogName , find) -VALUES('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); +INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) + VALUES + ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); diff --git a/db/changes/10420-valentines/00-docuwareConfig.sql b/db/changes/10420-valentines/00-docuwareConfig.sql index 0ef190cb79..c2c78c67e8 100644 --- a/db/changes/10420-valentines/00-docuwareConfig.sql +++ b/db/changes/10420-valentines/00-docuwareConfig.sql @@ -2,8 +2,4 @@ CREATE TABLE `vn`.`docuwareConfig` ( `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY, `url` varchar(75) NULL, `token` varchar(1000) DEFAULT NULL -); - -INSERT INTO `vn`.`docuwareConfig` -(url, token) -VALUES('https://verdnatura.docuware.cloud/docuware/platform/', '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'); +); \ No newline at end of file diff --git a/db/dump/fixtures.sql b/db/dump/fixtures.sql index 07eaf23fdd..7c7709716a 100644 --- a/db/dump/fixtures.sql +++ b/db/dump/fixtures.sql @@ -2443,3 +2443,11 @@ INSERT INTO `bs`.`defaulter` (`clientFk`, `amount`, `created`, `defaulterSinced` (1103, 500, CURDATE(), CURDATE()), (1107, 500, CURDATE(), CURDATE()), (1109, 500, CURDATE(), CURDATE()); + +INSERT INTO `vn`.`docuwareConfig` (`url`, `token`) + VALUES + ('https://verdnatura.docuware.cloud/docuware/platform', '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'); + +INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) + VALUES + ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); \ No newline at end of file diff --git a/loopback/server/datasources.json b/loopback/server/datasources.json index 0df03882c3..27921c78a3 100644 --- a/loopback/server/datasources.json +++ b/loopback/server/datasources.json @@ -83,5 +83,16 @@ "application/octet-stream", "application/pdf" ] + }, + "docuwareStorage": { + "name": "docuwareStorage", + "connector": "loopback-component-storage", + "provider": "filesystem", + "root": "./storage/pdfs/docuware", + "maxFileSize": "52428800", + "allowedContentTypes": [ + "application/octet-stream", + "application/pdf" + ] } } \ No newline at end of file diff --git a/modules/invoiceOut/back/methods/invoiceOut/docuware.js b/modules/invoiceOut/back/methods/invoiceOut/docuware.js deleted file mode 100644 index aa58aaed17..0000000000 --- a/modules/invoiceOut/back/methods/invoiceOut/docuware.js +++ /dev/null @@ -1,65 +0,0 @@ -const got = require('got'); -const {createWriteStream} = require('fs'); -const UserError = require('vn-loopback/util/user-error'); - -module.exports = Self => { - Self.remoteMethodCtx('docuware', { - description: 'Download an invoice PDF', - accessType: 'READ', - accepts: [ - { - arg: 'ticketId', - type: 'number', - description: 'The invoiceable ticket id' - }, - ], - returns: { - type: 'object', - root: true - }, - http: { - path: `/docuware`, - verb: 'POST' - } - }); - - Self.docuware = async function(ctx, ticketId) { - // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; - // hay que crear tambien una busqueda por cada fileCabinet - // columnas necesarias. seccion, fileCabinet, DBName, dialog - const models = Self.app.models; - const docuwareInfo = await models.Docuware.findOne({ - where: { - name: 'albaran' - } - }); - console.log(docuwareInfo); - const fileCabinet = docuwareInfo.fileCabinet; - const find = docuwareInfo.find; - const dialog = docuwareInfo.dialog; - const docuwareUrl = `https://verdnatura.docuware.cloud/docuware/platform/FileCabinets/${fileCabinet}`; - const cookie = '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'; - - // get DocuwareID - const dialogOptions = { - 'headers': { - 'Accept': 'application/json', - 'Content-Type': 'application/json', - 'Cookie': cookie - }, - 'body': JSON.stringify({'Condition': [{DBName: find, Value: [ticketId]}]}) - }; - const response = await got.post(`${docuwareUrl}/Query/DialogExpression?dialogId=${dialog}`, dialogOptions); - const docuwareId = JSON.parse(response.body).Items[0].Id; - - // download file - const downloadUrl = `${docuwareUrl}/Documents/${docuwareId}/FileDownload?targetFileType=Auto&keepAnnotations=false`; - const downloadOptions = { - 'headers': { - 'Cookie': cookie - } - }; - - await got.stream(downloadUrl, downloadOptions).pipe(createWriteStream(`${ticketId}_${docuwareId}.pdf`)); - }; -}; diff --git a/modules/invoiceOut/back/models/invoice-out.js b/modules/invoiceOut/back/models/invoice-out.js index 3da5aedc69..3b2822ada1 100644 --- a/modules/invoiceOut/back/models/invoice-out.js +++ b/modules/invoiceOut/back/models/invoice-out.js @@ -3,7 +3,6 @@ module.exports = Self => { require('../methods/invoiceOut/summary')(Self); require('../methods/invoiceOut/getTickets')(Self); require('../methods/invoiceOut/download')(Self); - require('../methods/invoiceOut/docuware')(Self); require('../methods/invoiceOut/delete')(Self); require('../methods/invoiceOut/book')(Self); require('../methods/invoiceOut/createPdf')(Self); diff --git a/modules/ticket/front/descriptor-menu/index.html b/modules/ticket/front/descriptor-menu/index.html index ae5642cf32..87a8217465 100644 --- a/modules/ticket/front/descriptor-menu/index.html +++ b/modules/ticket/front/descriptor-menu/index.html @@ -20,14 +20,22 @@ - Show as PDF + as PDF + + as DOCUWARE + - Show as CSV + as CSV diff --git a/modules/ticket/front/descriptor-menu/index.js b/modules/ticket/front/descriptor-menu/index.js index 9d4381f7c5..6abdfcce6a 100644 --- a/modules/ticket/front/descriptor-menu/index.js +++ b/modules/ticket/front/descriptor-menu/index.js @@ -82,6 +82,7 @@ class Controller extends Section { return this.$http.get(`Tickets/${this.ticketId}`, {filter}) .then(res => this.ticket = res.data) .then(() => { + this.hasDocuware(); this.canStowaway(); this.isTicketEditable(); }); @@ -122,6 +123,13 @@ class Controller extends Section { }); } + hasDocuware() { + this.$http.get(`Docuwares/${this.id}/checkFile`) + .then(res => { + this.hasDocuware = res.data; + }); + } + showCsvDeliveryNote() { this.vnReport.showCsv('delivery-note', { recipientId: this.ticket.client.id, diff --git a/modules/ticket/front/descriptor-menu/locale/es.yml b/modules/ticket/front/descriptor-menu/locale/es.yml index 1f4ee710cb..4a61556db8 100644 --- a/modules/ticket/front/descriptor-menu/locale/es.yml +++ b/modules/ticket/front/descriptor-menu/locale/es.yml @@ -1,7 +1,7 @@ Show Delivery Note...: Ver albarán... Send Delivery Note...: Enviar albarán... -Show as PDF: Ver como PDF -Show as CSV: Ver como CSV +as PDF: como PDF +as CSV: como CSV Send PDF: Enviar PDF Send CSV: Enviar CSV Send CSV Delivery Note: Enviar albarán en CSV From 89eee042b55327b880352010253da54768ccfd30 Mon Sep 17 00:00:00 2001 From: alexm Date: Thu, 17 Feb 2022 08:02:02 +0100 Subject: [PATCH 08/31] refactor(ticket_basic-data): zeroFill and move getMovable --- .../00-ticket_getMovable.sql | 0 modules/ticket/front/basic-data/step-two/index.html | 2 +- 2 files changed, 1 insertion(+), 1 deletion(-) rename db/changes/{10411-january => 10420-valentines}/00-ticket_getMovable.sql (100%) diff --git a/db/changes/10411-january/00-ticket_getMovable.sql b/db/changes/10420-valentines/00-ticket_getMovable.sql similarity index 100% rename from db/changes/10411-january/00-ticket_getMovable.sql rename to db/changes/10420-valentines/00-ticket_getMovable.sql diff --git a/modules/ticket/front/basic-data/step-two/index.html b/modules/ticket/front/basic-data/step-two/index.html index af06a0f70b..6be455fc9e 100644 --- a/modules/ticket/front/basic-data/step-two/index.html +++ b/modules/ticket/front/basic-data/step-two/index.html @@ -23,7 +23,7 @@ title="{{::sale.item.name}}" vn-click-stop="itemDescriptor.show($event, sale.itemFk, sale.id)" class="link"> - {{("000000"+sale.itemFk).slice(-6)}} + {{::sale.itemFk | zeroFill:6}}
From 72f4ef70ed3393ed031b2a34055ecb65da802559 Mon Sep 17 00:00:00 2001 From: vicent Date: Thu, 17 Feb 2022 10:18:47 +0100 Subject: [PATCH 09/31] recalculate neto in sql --- print/templates/reports/invoice/sql/intrastat.sql | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/print/templates/reports/invoice/sql/intrastat.sql b/print/templates/reports/invoice/sql/intrastat.sql index e391056ec5..6bf72c158a 100644 --- a/print/templates/reports/invoice/sql/intrastat.sql +++ b/print/templates/reports/invoice/sql/intrastat.sql @@ -2,9 +2,13 @@ SELECT ir.id AS code, ir.description AS description, CAST(SUM(IFNULL(i.stems,1) * s.quantity) AS DECIMAL(10,2)) as stems, - CAST(SUM( weight) AS DECIMAL(10,2)) as netKg, + CAST(SUM(IF(sv.physicalWeight, sv.physicalWeight, i.density * sub.cm3delivery/1000000)) AS DECIMAL(10,2)) netKg, CAST(SUM((s.quantity * s.price * (100 - s.discount) / 100 )) AS DECIMAL(10,2)) AS subtotal - FROM vn.sale s + FROM vn.sale s + LEFT JOIN (SELECT ic.itemFk, ic.cm3, ic.cm3delivery + FROM vn.itemCost ic + WHERE ic.cm3 + GROUP BY ic.itemFk) sub ON s.itemFk = sub.itemFk LEFT JOIN vn.saleVolume sv ON sv.saleFk = s.id LEFT JOIN vn.ticket t ON t.id = s.ticketFk LEFT JOIN vn.invoiceOut io ON io.ref = t.refFk From 0f4649c50f5addfdeacda0ee546604b459658a0a Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 21 Feb 2022 08:48:53 +0100 Subject: [PATCH 10/31] feat(ticket_descriptor-menu): docuware implemented --- back/methods/docuware/checkFile.js | 77 +++--- back/methods/docuware/download.js | 124 ++++------ back/methods/docuware/specs/checkFile.spec.js | 163 ++++-------- back/methods/docuware/specs/download.spec.js | 44 +++- back/model-config.json | 3 - back/models/docuware-container.json | 10 - db/changes/10420-valentines/00-docuware.sql | 2 +- db/dump/fixtures.sql | 6 +- loopback/server/datasources.json | 11 - .../front/descriptor-menu/index.html | 234 +++++++++--------- .../invoiceOut/front/descriptor-menu/index.js | 13 - .../ticket/front/descriptor-menu/index.html | 4 +- modules/ticket/front/descriptor-menu/index.js | 8 +- .../front/descriptor-menu/index.spec.js | 11 +- 14 files changed, 312 insertions(+), 398 deletions(-) delete mode 100644 back/models/docuware-container.json diff --git a/back/methods/docuware/checkFile.js b/back/methods/docuware/checkFile.js index 7dc1993f04..a674707fc2 100644 --- a/back/methods/docuware/checkFile.js +++ b/back/methods/docuware/checkFile.js @@ -1,16 +1,27 @@ const got = require('got'); -const UserError = require('vn-loopback/util/user-error'); module.exports = Self => { Self.remoteMethodCtx('checkFile', { - description: 'Download an docuware PDF', + description: 'Check if exist docuware file', accessType: 'READ', accepts: [ { arg: 'id', - type: 'String', - description: 'The invoice id', + type: 'number', + description: 'The id', http: {source: 'path'} + }, + { + arg: 'fileCabinet', + type: 'string', + required: true, + description: 'The fileCabinet name' + }, + { + arg: 'dialog', + type: 'string', + required: true, + description: 'The dialog name' } ], returns: { @@ -19,21 +30,21 @@ module.exports = Self => { }, http: { path: `/:id/checkFile`, - verb: 'GET' + verb: 'POST' } }); - Self.checkFile = async function(ctx, id) { - // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; - // hay que crear tambien una busqueda por cada fileCabinet - // columnas necesarias. seccion, fileCabinet, DBName, dialog + Self.checkFile = async function(ctx, id, fileCabinet, dialog) { + const myUserId = ctx.req.accessToken.userId; + if (!myUserId) + return false; const models = Self.app.models; const docuwareConfig = await models.DocuwareConfig.findOne(); const docuwareInfo = await models.Docuware.findOne({ where: { - name: 'deliveryClient', - dialogName: 'findTicket' + name: fileCabinet, + dialogName: dialog } }); @@ -41,7 +52,6 @@ module.exports = Self => { const cookie = docuwareConfig.token; const fileCabinetName = docuwareInfo.fileCabinetName; const find = docuwareInfo.find; - const options = { 'headers': { 'Accept': 'application/json', @@ -49,29 +59,32 @@ module.exports = Self => { 'Cookie': cookie } }; - // get fileCabinetId - const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options).json(); - const fileCabinetId = fileCabinetResponse.FileCabinet.find(dialogs => dialogs.Name === fileCabinetName).Id; - - // get dialog - const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options).json(); - const dialogId = dialogResponse.Dialog.find(dialogs => dialogs.DisplayName === 'find').Id; - - // get docuwareID - const docuwareOptions = { - 'headers': { - 'Accept': 'application/json', - 'Content-Type': 'application/json', - 'Cookie': cookie - }, - 'body': JSON.stringify({'Condition': [{DBName: find, Value: [id]}]}) + const condtions = { + condition: [ + { + DBName: find, + Value: [id] + } + ] }; - const response = await got.post( - `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, - docuwareOptions - ); + try { + // get fileCabinetId + const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options); + const fileCabinetJson = JSON.parse(fileCabinetResponse.body).FileCabinet; + const fileCabinetId = fileCabinetJson.find(dialogs => dialogs.Name === fileCabinetName).Id; + + // get dialog + const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options); + const dialogJson = JSON.parse(dialogResponse.body).Dialog; + const dialogId = dialogJson.find(dialogs => dialogs.DisplayName === 'find').Id; + + // get docuwareID + Object.assign(options, {'body': JSON.stringify(condtions)}); + const response = await got.post( + `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, options); JSON.parse(response.body).Items[0].Id; + return true; } catch (error) { return false; diff --git a/back/methods/docuware/download.js b/back/methods/docuware/download.js index a2a95fcd18..75789d1878 100644 --- a/back/methods/docuware/download.js +++ b/back/methods/docuware/download.js @@ -1,9 +1,6 @@ +/* eslint max-len: ["error", { "code": 180 }]*/ const got = require('got'); -const fs = require('fs-extra'); -const path = require('path'); const UserError = require('vn-loopback/util/user-error'); -const {promisify} = require('util'); -const nodeStream = require('stream'); module.exports = Self => { Self.remoteMethodCtx('download', { @@ -13,7 +10,19 @@ module.exports = Self => { { arg: 'id', type: 'number', - description: 'The ticket id', + description: 'The id', + http: {source: 'path'} + }, + { + arg: 'fileCabinet', + type: 'string', + description: 'The id', + http: {source: 'path'} + }, + { + arg: 'dialog', + type: 'string', + description: 'The id', http: {source: 'path'} } ], @@ -24,34 +33,31 @@ module.exports = Self => { root: true }, { arg: 'Content-Type', - type: 'String', + type: 'string', http: {target: 'header'} }, { arg: 'Content-Disposition', - type: 'String', + type: 'string', http: {target: 'header'} } ], http: { - path: `/:id/download`, + path: `/:id/download/:fileCabinet/:dialog`, verb: 'GET' } }); - Self.download = async function(ctx, id) { - // const fileCabinet = 'ad2c49df-8976-4941-bb19-9b30685f14a4'; - // hay que crear tambien una busqueda por cada fileCabinet - // columnas necesarias. seccion, fileCabinet, DBName, dialog - /* const myUserId = ctx.req.accessToken.userId; + Self.download = async function(ctx, id, fileCabinet, dialog) { + const myUserId = ctx.req.accessToken.userId; if (!myUserId) - throw new UserError(`You don't have enough privileges`);*/ + throw new UserError(`You don't have enough privileges`); const models = Self.app.models; const docuwareConfig = await models.DocuwareConfig.findOne(); const docuwareInfo = await models.Docuware.findOne({ where: { - name: 'deliveryClient', - dialogName: 'findTicket' + name: fileCabinet, + dialogName: dialog } }); @@ -59,7 +65,6 @@ module.exports = Self => { const cookie = docuwareConfig.token; const fileCabinetName = docuwareInfo.fileCabinetName; const find = docuwareInfo.find; - const options = { 'headers': { 'Accept': 'application/json', @@ -67,71 +72,44 @@ module.exports = Self => { 'Cookie': cookie } }; - // get fileCabinetId - const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options).json(); - const fileCabinetId = fileCabinetResponse.FileCabinet.find(dialogs => dialogs.Name === fileCabinetName).Id; - - // get dialog - const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options).json(); - const dialogId = dialogResponse.Dialog.find(dialogs => dialogs.DisplayName === 'find').Id; - - // get docuwareID - const docuwareOptions = { - 'headers': { - 'Accept': 'application/json', - 'Content-Type': 'application/json', - 'Cookie': cookie - }, - 'body': JSON.stringify({'Condition': [{DBName: find, Value: [0]}]}) - }; - const response = await got.post( - `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, - docuwareOptions - ); - const docuwareId = JSON.parse(response.body).Items[0].Id; - - // download file - const downloadUrl = `${docuwareUrl}/FileCabinets/${fileCabinetId}/Documents/${docuwareId}/FileDownload?targetFileType=Auto&keepAnnotations=false`; - const downloadOptions = { - 'headers': { - 'Cookie': cookie - } + const condtions = { + condition: [ + { + DBName: find, + Value: [id] + } + ] }; try { - // save file - const ticket = await models.Ticket.findById(id); + // get fileCabinetId + const fileCabinetResponse = await got.get(`${docuwareUrl}/FileCabinets`, options); + const fileCabinetJson = JSON.parse(fileCabinetResponse.body).FileCabinet; + const fileCabinetId = fileCabinetJson.find(dialogs => dialogs.Name === fileCabinetName).Id; - const shipped = ticket.shipped; - const year = shipped.getFullYear().toString(); - const month = (shipped.getMonth() + 1).toString(); - const day = shipped.getDate().toString(); - const fileName = `${year}${id}.pdf`; + // get dialog + const dialogResponse = await got.get(`${docuwareUrl}/FileCabinets/${fileCabinetId}/dialogs`, options); + const dialogJson = JSON.parse(dialogResponse.body).Dialog; + const dialogId = dialogJson.find(dialogs => dialogs.DisplayName === 'find').Id; - const container = await models.DocuwareContainer.container(year); - const rootPath = container.client.root; - const src = path.join(rootPath, year, month, day); - const fileSrc = path.join(src, fileName); + // get docuwareID + Object.assign(options, {'body': JSON.stringify(condtions)}); + const response = await got.post(`${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, options); + const docuwareId = JSON.parse(response.body).Items[0].Id; - await fs.mkdir(src, {recursive: true}); - - const pipeline = promisify(nodeStream.pipeline); - await pipeline( - got.stream(downloadUrl, downloadOptions), - fs.createWriteStream(fileSrc) - ); - - // open file - const file = { - path: fileSrc, - contentType: 'application/pdf', - name: fileName + // download & save file + const fileName = `filename="${id}.pdf"`; + const contentType = 'application/pdf'; + const downloadUri = `${docuwareUrl}/FileCabinets/${fileCabinetId}/Documents/${docuwareId}/FileDownload?targetFileType=Auto&keepAnnotations=false`; + const downloadOptions = { + 'headers': { + 'Cookie': cookie + } }; - await fs.access(file.path); - let stream = fs.createReadStream(file.path); + const stream = got.stream(downloadUri, downloadOptions); - return [stream, file.contentType, `filename="${file.name}"`]; + return [stream, contentType, fileName]; } catch (error) { if (error.code === 'ENOENT') throw new UserError('The DOCUWARE PDF document does not exists'); diff --git a/back/methods/docuware/specs/checkFile.spec.js b/back/methods/docuware/specs/checkFile.spec.js index 7cb2ae6f92..2ebde0df4b 100644 --- a/back/methods/docuware/specs/checkFile.spec.js +++ b/back/methods/docuware/specs/checkFile.spec.js @@ -1,129 +1,64 @@ -const app = require('vn-loopback/server/server'); +const models = require('vn-loopback/server/server').models; +const got = require('got'); -describe('image upload()', () => { - describe('as buyer', () => { - const buyerId = 35; - const workerId = 1106; - const itemId = 4; +describe('docuware download()', () => { + const ticketId = 1; + const userId = 9; + const ctx = { + req: { - it('should try to upload a file for the collection "catalog" and throw a privileges error', async() => { - const ctx = {req: {accessToken: {userId: buyerId}}, - args: { - id: workerId, - collection: 'user' - } - }; + accessToken: {userId: userId}, + headers: {origin: 'http://localhost:5000'}, + } + }; - let error; - try { - await app.models.Image.upload(ctx); - } catch (err) { - error = err; - } + const fileCabinetName = 'deliveryClientTest'; + const dialogDisplayName = 'find'; + const dialogName = 'findTest'; - expect(error.message).toEqual(`You don't have enough privileges`); - }); + const gotGetResponse = { + body: JSON.stringify( + { + FileCabinet: [ + {Id: 12, Name: fileCabinetName} + ], + Dialog: [ + {Id: 34, DisplayName: dialogDisplayName} + ] + }) + }; - it('should call to the TempContainer upload method for the collection "catalog"', async() => { - const containerModel = app.models.TempContainer; - spyOn(containerModel, 'upload'); + it('should return exist file in docuware', async() => { + const gotPostResponse = { + body: JSON.stringify( + { + Items: [ + {Id: 56} + ], + }) + }; - const ctx = {req: {accessToken: {userId: buyerId}}, - args: { - id: itemId, - collection: 'catalog' - } - }; + spyOn(got, 'get').and.returnValue(new Promise(resolve => resolve(gotGetResponse))); + spyOn(got, 'post').and.returnValue(new Promise(resolve => resolve(gotPostResponse))); - try { - await app.models.Image.upload(ctx); - } catch (err) { } + const result = await models.Docuware.checkFile(ctx, ticketId, fileCabinetName, dialogName); - expect(containerModel.upload).toHaveBeenCalled(); - }); + expect(result).toEqual(true); }); - describe('as marketing', () => { - const marketingId = 51; - const workerId = 1106; - const itemId = 4; + it('should return not exist file in docuware', async() => { + const gotPostResponse = { + body: JSON.stringify( + { + Items: [], + }) + }; - it('should be able to call to the TempContainer upload method for the collection "user"', async() => { - const containerModel = app.models.TempContainer; - spyOn(containerModel, 'upload'); + spyOn(got, 'get').and.returnValue(new Promise(resolve => resolve(gotGetResponse))); + spyOn(got, 'post').and.returnValue(new Promise(resolve => resolve(gotPostResponse))); - const ctx = {req: {accessToken: {userId: marketingId}}, - args: { - id: workerId, - collection: 'user' - } - }; + const result = await models.Docuware.checkFile(ctx, ticketId, fileCabinetName, dialogName); - try { - await app.models.Image.upload(ctx); - } catch (err) { } - - expect(containerModel.upload).toHaveBeenCalled(); - }); - - it('should be able to call to the TempContainer upload method for the collection "catalog"', async() => { - const containerModel = app.models.TempContainer; - spyOn(containerModel, 'upload'); - - const ctx = {req: {accessToken: {userId: marketingId}}, - args: { - id: itemId, - collection: 'catalog' - } - }; - - try { - await app.models.Image.upload(ctx); - } catch (err) { } - - expect(containerModel.upload).toHaveBeenCalled(); - }); - }); - - describe('as hhrr', () => { - const hhrrId = 37; - const workerId = 1106; - const itemId = 4; - - it('should upload a file for the collection "user" and call to the TempContainer upload method', async() => { - const containerModel = app.models.TempContainer; - spyOn(containerModel, 'upload'); - - const ctx = {req: {accessToken: {userId: hhrrId}}, - args: { - id: itemId, - collection: 'user' - } - }; - - try { - await app.models.Image.upload(ctx); - } catch (err) { } - - expect(containerModel.upload).toHaveBeenCalled(); - }); - - it('should try to upload a file for the collection "catalog" and throw a privilege error', async() => { - const ctx = {req: {accessToken: {userId: hhrrId}}, - args: { - id: workerId, - collection: 'catalog' - } - }; - - let error; - try { - await app.models.Image.upload(ctx); - } catch (err) { - error = err; - } - - expect(error.message).toEqual(`You don't have enough privileges`); - }); + expect(result).toEqual(false); }); }); diff --git a/back/methods/docuware/specs/download.spec.js b/back/methods/docuware/specs/download.spec.js index 4bdf800b48..436063fd8e 100644 --- a/back/methods/docuware/specs/download.spec.js +++ b/back/methods/docuware/specs/download.spec.js @@ -1,9 +1,10 @@ const models = require('vn-loopback/server/server').models; -const fs = require('fs-extra'); +const got = require('got'); +const stream = require('stream'); -describe('image download()', () => { +describe('docuware download()', () => { const userId = 9; - const invoiceId = 1; + const ticketId = 1; const ctx = { req: { @@ -13,16 +14,37 @@ describe('image download()', () => { }; it('should return the downloaded file name', async() => { - spyOn(models.DocuwareContainer, 'container').and.returnValue({ - client: {root: '/path'} - }); - spyOn(fs, 'createReadStream').and.returnValue(new Promise(resolve => resolve('streamObject'))); - spyOn(fs, 'access').and.returnValue(true); - spyOn(models.InvoiceOut, 'createPdf').and.returnValue(new Promise(resolve => resolve(true))); + const fileCabinetName = 'deliveryClientTest'; + const dialogDisplayName = 'find'; + const dialogName = 'findTest'; + const gotGetResponse = { + body: JSON.stringify( + { + FileCabinet: [ + {Id: 12, Name: fileCabinetName} + ], + Dialog: [ + {Id: 34, DisplayName: dialogDisplayName} + ] + }) + }; - const result = await models.InvoiceOut.download(ctx, invoiceId); + const gotPostResponse = { + body: JSON.stringify( + { + Items: [ + {Id: 56} + ], + }) + }; + + spyOn(got, 'get').and.returnValue(new Promise(resolve => resolve(gotGetResponse))); + spyOn(got, 'post').and.returnValue(new Promise(resolve => resolve(gotPostResponse))); + spyOn(got, 'stream').and.returnValue(new stream.PassThrough({objectMode: true})); + + const result = await models.Docuware.download(ctx, ticketId, fileCabinetName, dialogName); expect(result[1]).toEqual('application/pdf'); - expect(result[2]).toMatch(/filename="\d{4}T1111111.pdf"/); + expect(result[2]).toEqual(`filename="${ticketId}.pdf"`); }); }); diff --git a/back/model-config.json b/back/model-config.json index f1b6623546..4c79d565b8 100644 --- a/back/model-config.json +++ b/back/model-config.json @@ -50,9 +50,6 @@ "DocuwareConfig": { "dataSource": "vn" }, - "DocuwareContainer": { - "dataSource": "docuwareStorage" - }, "EmailUser": { "dataSource": "vn" }, diff --git a/back/models/docuware-container.json b/back/models/docuware-container.json deleted file mode 100644 index 8180695c18..0000000000 --- a/back/models/docuware-container.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "name": "DocuwareContainer", - "base": "Container", - "acls": [{ - "accessType": "READ", - "principalType": "ROLE", - "principalId": "$everyone", - "permission": "ALLOW" - }] -} \ No newline at end of file diff --git a/db/changes/10420-valentines/00-docuware.sql b/db/changes/10420-valentines/00-docuware.sql index ca4b0a1142..e5311252dd 100644 --- a/db/changes/10420-valentines/00-docuware.sql +++ b/db/changes/10420-valentines/00-docuware.sql @@ -8,4 +8,4 @@ CREATE TABLE `vn`.`docuware` ( INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) VALUES - ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); + ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); \ No newline at end of file diff --git a/db/dump/fixtures.sql b/db/dump/fixtures.sql index 7c7709716a..74568ebc72 100644 --- a/db/dump/fixtures.sql +++ b/db/dump/fixtures.sql @@ -2444,10 +2444,6 @@ INSERT INTO `bs`.`defaulter` (`clientFk`, `amount`, `created`, `defaulterSinced` (1107, 500, CURDATE(), CURDATE()), (1109, 500, CURDATE(), CURDATE()); -INSERT INTO `vn`.`docuwareConfig` (`url`, `token`) - VALUES - ('https://verdnatura.docuware.cloud/docuware/platform', '.DWPLATFORMAUTH=66C7DCD2B9365EF974AFEB43F61715152082EF39C649CB1506F9ACC34DD54C5B34944DDFBF97EAE5C5147063850B16B3B9FFFB2232FDD03F35B51B1305D5E1E7DB833F6AC560C739E40778932C8BCC64DA7ECE64B0B1F71A3DB986B3710DFA4C061776F9C61DDAA60EF30F7F37FB8733BF4B1830F98102E403E4E751F13F31B582AEDF5B33A25346E10CA34A8559F0CD6ACA39A7379AC67BE061CD27531D02675123FB0D254426E306EC6FA49DED7CF30EBBAD8365BE60D7E919D4AD2EB8F9CD94424DFCD95151C0F6DD3EE8569A7CA4A30D1A3F42DA9DD368A33955A4AFE9CB4FCCC230801BC645AA87A68EC33F6BD165D5A0F02B63D5D832AF936B9398EC428D4ACD41E56848A2CDF797C99226BB2AC48EB5F9C1C5D8C1C7F6A7F67F455ABAC1DBC7443521876B588F369CAE6EC81747BA3134F7EE2662DA296FC2C16528B0AB4839EEE6EE79A82AA3888E4AB53FEC6FFAD26A592ABD76441AFCD634097D0B0B57E16A510D0E6F769710C6F4BDB1476CCDE0967788B90A67BADFB7E37B1F7F60C879A0E9D75AD2BA6647FC11477305B44512AF408845E6099CF64B7A3D77EE; ApplicationGatewayAffinity=c5fad6cb3332163516d49258a1ebf52c; ApplicationGatewayAffinityCORS=c5fad6cb3332163516d49258a1ebf52c; DWPLATFORMBROWSERID=C2173B1A1FE42B449AA12C8465561991BA4664AFA9F44D4C9DD8748FF92EFEBF629E4A75860747C4D8290F70344385CCAFE3EAFD8814CF44F452275C95E89D19D35A178D0BCC6930EF07AC7CF91672F7CB43C2B54CDFAE52BDF17C467FFFE3411FE0D792E4F513726F295648DDE627DF2C6288C89086E2DE6916E4B0A5291AA7C269015A5328147783EC15FB8EF43EE5DAE5A6CD3D318570670234176CAE7B19D9812D3F09D731C5A27A621B39D0564C81774FA993160AAAD833CC75634445B7B47C5A2E26004FF914606B5B0CB897A694F26AD5E80A1EE0D3B7BA4881F8A570'); - INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) VALUES - ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); \ No newline at end of file + ('deliveryClientTest', 'deliveryClientTest', 'findTest', 'word'); \ No newline at end of file diff --git a/loopback/server/datasources.json b/loopback/server/datasources.json index 27921c78a3..0df03882c3 100644 --- a/loopback/server/datasources.json +++ b/loopback/server/datasources.json @@ -83,16 +83,5 @@ "application/octet-stream", "application/pdf" ] - }, - "docuwareStorage": { - "name": "docuwareStorage", - "connector": "loopback-component-storage", - "provider": "filesystem", - "root": "./storage/pdfs/docuware", - "maxFileSize": "52428800", - "allowedContentTypes": [ - "application/octet-stream", - "application/pdf" - ] } } \ No newline at end of file diff --git a/modules/invoiceOut/front/descriptor-menu/index.html b/modules/invoiceOut/front/descriptor-menu/index.html index 070da18e12..345e67d95e 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.html +++ b/modules/invoiceOut/front/descriptor-menu/index.html @@ -1,144 +1,138 @@ +icon="more_vert" +vn-popover="menu"> - - - Show invoice... + + + Show invoice... + + + + Show as PDF + + + Show as CSV + + + + + + Send invoice... - - - - Show as PDF - - - Show as DOCUWARE - - - Show as CSV - - - - - - Send invoice... - - - - - Send PDF - - - Send CSV - - - - - - Delete Invoice - - - Book invoice - - - {{!$ctrl.invoiceOut.hasPdf ? 'Generate PDF invoice': 'Regenerate PDF invoice'}} - - - Show CITES letter - - + + + + Send PDF + + + Send CSV + + + + + + Delete Invoice + + + Book invoice + + + {{!$ctrl.invoiceOut.hasPdf ? 'Generate PDF invoice': 'Regenerate PDF invoice'}} + + + Show CITES letter + + +vn-id="deleteConfirmation" +on-accept="$ctrl.deleteInvoiceOut()" +question="Are you sure you want to delete this invoice?"> +vn-id="bookConfirmation" +on-accept="$ctrl.bookInvoiceOut()" +question="Are you sure you want to book this invoice?"> +vn-id="clientDescriptor"> +vn-id="createInvoicePdfConfirmation" +on-accept="$ctrl.createPdfInvoice()" +question="Are you sure you want to generate/regenerate the PDF invoice?" +message="Generate PDF invoice document"> - - Are you sure you want to send it? - - - - - - - +vn-id="sendPdfConfirmation" +on-accept="$ctrl.sendPdfInvoice($data)" +message="Send PDF invoice"> + + Are you sure you want to send it? + + + + + + + - - Are you sure you want to send it? - - - - - - - +vn-id="sendCsvConfirmation" +on-accept="$ctrl.sendCsvInvoice($data)" +message="Send CSV invoice"> + + Are you sure you want to send it? + + + + + + + \ No newline at end of file diff --git a/modules/invoiceOut/front/descriptor-menu/index.js b/modules/invoiceOut/front/descriptor-menu/index.js index f6855795a5..7738845f97 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.js +++ b/modules/invoiceOut/front/descriptor-menu/index.js @@ -88,19 +88,6 @@ class Controller extends Section { }); } - downloadDocuware() { - const options = { - ticketId: 3367050 - }; - - return this.$http.post(`Docuwares/download`, options) - .then(() => { - const snackbarMessage = this.$t( - `The invoice PDF document has been downloaded`); - this.vnApp.showSuccess(snackbarMessage); - }); - } - sendPdfInvoice($data) { if (!$data.email) return this.vnApp.showError(this.$t(`The email can't be empty`)); diff --git a/modules/ticket/front/descriptor-menu/index.html b/modules/ticket/front/descriptor-menu/index.html index 87a8217465..2439bfb64a 100644 --- a/modules/ticket/front/descriptor-menu/index.html +++ b/modules/ticket/front/descriptor-menu/index.html @@ -27,10 +27,10 @@ - as DOCUWARE + as PDF this.ticket = res.data) .then(() => { - this.hasDocuware(); this.canStowaway(); this.isTicketEditable(); + this.hasDocuware(); }); } @@ -124,7 +124,11 @@ class Controller extends Section { } hasDocuware() { - this.$http.get(`Docuwares/${this.id}/checkFile`) + const params = { + fileCabinet: 'deliveryClient', + dialog: 'findTicket' + }; + this.$http.post(`Docuwares/${this.id}/checkFile`, params) .then(res => { this.hasDocuware = res.data; }); diff --git a/modules/ticket/front/descriptor-menu/index.spec.js b/modules/ticket/front/descriptor-menu/index.spec.js index 288c7508ba..0a80d08843 100644 --- a/modules/ticket/front/descriptor-menu/index.spec.js +++ b/modules/ticket/front/descriptor-menu/index.spec.js @@ -206,7 +206,8 @@ describe('Ticket Component vnTicketDescriptorMenu', () => { it('should make a query and show a success snackbar', () => { jest.spyOn(controller.vnApp, 'showSuccess'); - $httpBackend.whenGET(`Tickets/16`).respond(); + $httpBackend.whenPOST(`Docuwares/${ticket.id}/checkFile`).respond(); + $httpBackend.whenGET(`Tickets/${ticket.id}`).respond(); $httpBackend.expectPOST(`InvoiceOuts/${ticket.invoiceOut.id}/createPdf`).respond(); controller.createPdfInvoice(); $httpBackend.flush(); @@ -275,4 +276,12 @@ describe('Ticket Component vnTicketDescriptorMenu', () => { }); }); }); + + describe('hasDocuware()', () => { + it('should call hasDocuware method', () => { + $httpBackend.whenPOST(`Docuwares/${ticket.id}/checkFile`).respond(); + controller.hasDocuware(); + $httpBackend.flush(); + }); + }); }); From 32e3af0c257ce4d8782a2164b180cff240ad4e23 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 21 Feb 2022 08:53:37 +0100 Subject: [PATCH 11/31] tabulations --- .../front/descriptor-menu/index.html | 38 +++++++++---------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/modules/invoiceOut/front/descriptor-menu/index.html b/modules/invoiceOut/front/descriptor-menu/index.html index 345e67d95e..0e1d7c2abf 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.html +++ b/modules/invoiceOut/front/descriptor-menu/index.html @@ -1,7 +1,7 @@ + icon="more_vert" + vn-popover="menu"> @@ -80,32 +80,32 @@ vn-popover="menu"> + vn-id="deleteConfirmation" + on-accept="$ctrl.deleteInvoiceOut()" + question="Are you sure you want to delete this invoice?"> + vn-id="bookConfirmation" + on-accept="$ctrl.bookInvoiceOut()" + question="Are you sure you want to book this invoice?"> + vn-id="clientDescriptor"> + vn-id="createInvoicePdfConfirmation" + on-accept="$ctrl.createPdfInvoice()" + question="Are you sure you want to generate/regenerate the PDF invoice?" + message="Generate PDF invoice document"> + vn-id="sendPdfConfirmation" + on-accept="$ctrl.sendPdfInvoice($data)" + message="Send PDF invoice"> Are you sure you want to send it? + vn-id="sendCsvConfirmation" + on-accept="$ctrl.sendCsvInvoice($data)" + message="Send CSV invoice"> Are you sure you want to send it? Date: Mon, 21 Feb 2022 08:57:43 +0100 Subject: [PATCH 12/31] tabulations --- .../front/descriptor-menu/index.html | 183 +++++++++--------- 1 file changed, 91 insertions(+), 92 deletions(-) diff --git a/modules/invoiceOut/front/descriptor-menu/index.html b/modules/invoiceOut/front/descriptor-menu/index.html index 0e1d7c2abf..ea0f2eb5a4 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.html +++ b/modules/invoiceOut/front/descriptor-menu/index.html @@ -4,80 +4,79 @@ vn-popover="menu"> - - - Show invoice... - - - - Show as PDF - - - Show as CSV - - - - - - Send invoice... - - - - - Send PDF - - - Send CSV - - - - - - Delete Invoice - - - Book invoice - - - {{!$ctrl.invoiceOut.hasPdf ? 'Generate PDF invoice': 'Regenerate PDF invoice'}} - - - Show CITES letter - - + + + Show invoice... + + + + Show as PDF + + + Show as CSV + + + + + + Send invoice... + + + + Send PDF + + + Send CSV + + + + + + Delete Invoice + + + Book invoice + + + {{!$ctrl.invoiceOut.hasPdf ? 'Generate PDF invoice': 'Regenerate PDF invoice'}} + + + Show CITES letter + + - - Are you sure you want to send it? - - - - - - - + + Are you sure you want to send it? + + + + + + + @@ -124,13 +123,13 @@ vn-id="sendCsvConfirmation" on-accept="$ctrl.sendCsvInvoice($data)" message="Send CSV invoice"> - - Are you sure you want to send it? - - - + + Are you sure you want to send it? + + + From 6a5d49a53586769a67aba9991ea6410875670526 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 21 Feb 2022 08:59:42 +0100 Subject: [PATCH 13/31] tabulations --- modules/invoiceOut/front/descriptor-menu/index.html | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/modules/invoiceOut/front/descriptor-menu/index.html b/modules/invoiceOut/front/descriptor-menu/index.html index ea0f2eb5a4..859486ab17 100644 --- a/modules/invoiceOut/front/descriptor-menu/index.html +++ b/modules/invoiceOut/front/descriptor-menu/index.html @@ -130,8 +130,8 @@ ng-model="sendCsvConfirmation.data.email"> - - - - + + + + \ No newline at end of file From 8bbb5d5c27f7907ce606807f9446846b12d528b7 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 21 Feb 2022 11:28:00 +0100 Subject: [PATCH 14/31] variable name --- db/changes/10420-valentines/00-docuwareConfig.sql | 6 +++++- modules/ticket/front/descriptor-menu/index.html | 4 ++-- modules/ticket/front/descriptor-menu/index.js | 2 +- 3 files changed, 8 insertions(+), 4 deletions(-) diff --git a/db/changes/10420-valentines/00-docuwareConfig.sql b/db/changes/10420-valentines/00-docuwareConfig.sql index c2c78c67e8..1ba19af6d5 100644 --- a/db/changes/10420-valentines/00-docuwareConfig.sql +++ b/db/changes/10420-valentines/00-docuwareConfig.sql @@ -2,4 +2,8 @@ CREATE TABLE `vn`.`docuwareConfig` ( `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY, `url` varchar(75) NULL, `token` varchar(1000) DEFAULT NULL -); \ No newline at end of file +); + +INSERT INTO `vn`.`docuwareConfig` (`url`) + VALUES + ('https://verdnatura.docuware.cloud/docuware/platform'); \ No newline at end of file diff --git a/modules/ticket/front/descriptor-menu/index.html b/modules/ticket/front/descriptor-menu/index.html index 2439bfb64a..d613fb5de3 100644 --- a/modules/ticket/front/descriptor-menu/index.html +++ b/modules/ticket/front/descriptor-menu/index.html @@ -20,13 +20,13 @@ as PDF diff --git a/modules/ticket/front/descriptor-menu/index.js b/modules/ticket/front/descriptor-menu/index.js index 2af1b30c54..4304d85239 100644 --- a/modules/ticket/front/descriptor-menu/index.js +++ b/modules/ticket/front/descriptor-menu/index.js @@ -130,7 +130,7 @@ class Controller extends Section { }; this.$http.post(`Docuwares/${this.id}/checkFile`, params) .then(res => { - this.hasDocuware = res.data; + this.hasDocuwareFile = res.data; }); } From 812d79f2d56f69280f08b68b02a13e01520e3311 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 21 Feb 2022 15:11:39 +0100 Subject: [PATCH 15/31] feat(client_defaulter): implemented smart-table --- front/core/components/smart-table/table.scss | 5 + .../client/back/methods/defaulter/filter.js | 6 +- modules/client/front/defaulter/index.html | 216 ++++++++---------- modules/client/front/defaulter/index.js | 84 ++++++- modules/client/front/defaulter/index.spec.js | 31 ++- 5 files changed, 209 insertions(+), 133 deletions(-) diff --git a/front/core/components/smart-table/table.scss b/front/core/components/smart-table/table.scss index c38c149ca3..b40b988a78 100644 --- a/front/core/components/smart-table/table.scss +++ b/front/core/components/smart-table/table.scss @@ -99,6 +99,11 @@ smart-table table { } } } + & > td > textarea { + background-color: $color-font-light; + color: $color-font-bg; + width: 90%; + } } .vn-check { margin: 0; diff --git a/modules/client/back/methods/defaulter/filter.js b/modules/client/back/methods/defaulter/filter.js index c06d1c51b2..0a1d5093b9 100644 --- a/modules/client/back/methods/defaulter/filter.js +++ b/modules/client/back/methods/defaulter/filter.js @@ -58,16 +58,16 @@ module.exports = Self => { DISTINCT c.id clientFk, c.name clientName, c.salesPersonFk, - u.name salesPersonName, + u.nickname salesPersonName, d.amount, co.created, CONCAT(DATE(co.created), ' ', co.text) observation, uw.id workerFk, - uw.name workerName, + uw.nickname workerName, c.creditInsurance, d.defaulterSinced FROM vn.defaulter d - JOIN vn.client c ON c.id = d.clientFk + JOIN vn.client c ON c.id = d.clientFk LEFT JOIN vn.clientObservation co ON co.clientFk = c.id LEFT JOIN account.user u ON u.id = c.salesPersonFk LEFT JOIN account.user uw ON uw.id = co.workerFk diff --git a/modules/client/front/defaulter/index.html b/modules/client/front/defaulter/index.html index 121556df24..6d723c9759 100644 --- a/modules/client/front/defaulter/index.html +++ b/modules/client/front/defaulter/index.html @@ -15,17 +15,18 @@ model="model"> - - - -
+ + + +
Total
+ value="{{$ctrl.balanceDueTotal | currency: 'EUR': 2}}">
@@ -38,90 +39,98 @@ icon="icon-notes">
-
- - - - - - - - Client - Comercial - - Balance D. - - - Author - - Last observation - - Credit I. - - From - - - - - - - - - - - {{::defaulter.clientName}} - - - - - {{::defaulter.salesPersonName | dashIfEmpty}} - - - {{::defaulter.amount}} - - - {{::defaulter.workerName | dashIfEmpty}} - - - - - - - {{::defaulter.creditInsurance}} - {{::defaulter.defaulterSinced | date: 'dd/MM/yyyy'}} - - - -
-
+ + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + Client + + Comercial + + Balance D. + + Author + + Last observation + + Credit I. + + From +
+ + + + + {{::defaulter.clientName}} + + + + {{::defaulter.salesPersonName | dashIfEmpty}} + + {{::defaulter.amount | currency: 'EUR': 2}} + + {{::defaulter.workerName | dashIfEmpty}} + + + + {{::defaulter.creditInsurance | currency: 'EUR': 2}}{{::defaulter.defaulterSinced | date: 'dd/MM/yyyy'}}
+
+ + + vn-id="client-descriptor"> + vn-id="worker-descriptor"> - - - - - Filter by selection - - - Exclude selection - - - Remove filter - - - Remove all filters - - - Copy value - - - - 0) { - for (let defaulter of this.checked) - balanceDueTotal += defaulter.amount; - - return balanceDueTotal; - } + for (let defaulter of defaulters) + balanceDueTotal += defaulter.amount; return balanceDueTotal; } @@ -32,6 +85,22 @@ export default class Controller extends Section { return checkedLines; } + chipColor(date) { + const day = 24 * 60 * 60 * 1000; + const today = new Date(); + today.setHours(0, 0, 0, 0); + + const observationShipped = new Date(date); + observationShipped.setHours(0, 0, 0, 0); + + const difference = today - observationShipped; + + if (difference > (day * 20)) + return 'alert'; + if (difference > (day * 10)) + return 'warning'; + } + onResponse() { if (!this.defaulter.observation) throw new UserError(`The message can't be empty`); @@ -52,7 +121,10 @@ export default class Controller extends Section { exprBuilder(param, value) { switch (param) { + case 'observation': + return {[`observation`]: value}; case 'clientName': + case 'workerFk': case 'salesPersonFk': return {[`d.${param}`]: value}; } diff --git a/modules/client/front/defaulter/index.spec.js b/modules/client/front/defaulter/index.spec.js index 6428952ec6..8d6c8c307e 100644 --- a/modules/client/front/defaulter/index.spec.js +++ b/modules/client/front/defaulter/index.spec.js @@ -39,11 +39,7 @@ describe('client defaulter', () => { describe('balanceDueTotal() getter', () => { it('should return balance due total', () => { const data = controller.$.model.data; - data[1].checked = true; - data[2].checked = true; - - const checkedRows = controller.checked; - const expectedAmount = checkedRows[0].amount + checkedRows[1].amount; + const expectedAmount = data[0].amount + data[1].amount + data[2].amount; const result = controller.balanceDueTotal; @@ -51,6 +47,31 @@ describe('client defaulter', () => { }); }); + describe('chipColor()', () => { + it('should return undefined when the date is the present', () => { + let today = new Date(); + let result = controller.chipColor(today); + + expect(result).toEqual(undefined); + }); + + it('should return warning when the date is 10 days in the past', () => { + let pastDate = new Date(); + pastDate = pastDate.setDate(pastDate.getDate() - 11); + let result = controller.chipColor(pastDate); + + expect(result).toEqual('warning'); + }); + + it('should return alert when the date is 20 days in the past', () => { + let pastDate = new Date(); + pastDate = pastDate.setDate(pastDate.getDate() - 21); + let result = controller.chipColor(pastDate); + + expect(result).toEqual('alert'); + }); + }); + describe('onResponse()', () => { it('should return error for empty message', () => { let error; From 0d8dffac307d289086d7405345637e82be693a3a Mon Sep 17 00:00:00 2001 From: joan Date: Tue, 22 Feb 2022 07:30:26 +0100 Subject: [PATCH 16/31] refactor(chat): check rocketchat status before sending message --- back/methods/chat/getServiceAuth.js | 55 ++++++++++ back/methods/chat/send.js | 119 ++++------------------ back/methods/chat/sendCheckingPresence.js | 67 ++++++++---- back/models/chat.js | 1 + 4 files changed, 118 insertions(+), 124 deletions(-) create mode 100644 back/methods/chat/getServiceAuth.js diff --git a/back/methods/chat/getServiceAuth.js b/back/methods/chat/getServiceAuth.js new file mode 100644 index 0000000000..7eb0ceaa54 --- /dev/null +++ b/back/methods/chat/getServiceAuth.js @@ -0,0 +1,55 @@ +const axios = require('axios'); +const tokenLifespan = 10; +module.exports = Self => { + Self.remoteMethodCtx('getServiceAuth', { + description: 'Send a RocketChat message', + accessType: 'READ', + accepts: [], + returns: { + type: 'object', + root: true + }, + http: { + path: `/getServiceAuth`, + verb: 'GET' + } + }); + + Self.getServiceAuth = async() => { + if (!this.login) + this.login = await requestToken(); + + if (!this.login) return; + + if (Date.now() > this.login.expires) + this.login = await requestToken(); + + return this.login; + }; + + /** + * Requests a new Rocketchat token + */ + async function requestToken() { + const models = Self.app.models; + const chatConfig = await models.ChatConfig.findOne(); + + const {data} = await axios.post(`${chatConfig.api}/login`, { + user: chatConfig.user, + password: chatConfig.password + }); + + const requestData = data.data; + if (requestData) { + return { + host: chatConfig.host, + api: chatConfig.api, + auth: { + userId: requestData.userId, + token: requestData.authToken + }, + expires: Date.now() + (1000 * 60 * tokenLifespan) + }; + } + } +}; diff --git a/back/methods/chat/send.js b/back/methods/chat/send.js index 209dfb0352..5f79449456 100644 --- a/back/methods/chat/send.js +++ b/back/methods/chat/send.js @@ -1,4 +1,4 @@ -const got = require('got'); +const axios = require('axios'); module.exports = Self => { Self.remoteMethodCtx('send', { description: 'Send a RocketChat message', @@ -30,86 +30,12 @@ module.exports = Self => { const sender = await models.Account.findById(accessToken.userId); const recipient = to.replace('@', ''); - if (sender.name != recipient) { - let {body} = await sendMessage(sender, to, message); - if (body) - body = JSON.parse(body); - else - body = false; - - return body; - } - - return false; + if (sender.name != recipient) + return sendMessage(sender, to, message); }; async function sendMessage(sender, channel, message) { - const config = await getConfig(); - const avatar = `${config.host}/avatar/${sender.name}`; - const uri = `${config.api}/chat.postMessage`; - - return sendAuth(uri, { - 'channel': channel, - 'avatar': avatar, - 'alias': sender.nickname, - 'text': message - }).catch(async error => { - if (error.statusCode === 401) { - this.auth = null; - - return sendMessage(sender, channel, message); - } - - throw new Error(error.message); - }); - } - - /** - * Returns a rocketchat token - * @return {Object} userId and authToken - */ - async function getAuthToken() { - if (!this.auth || this.auth && !this.auth.authToken) { - const config = await getConfig(); - const uri = `${config.api}/login`; - let {body} = await send(uri, { - user: config.user, - password: config.password - }); - - if (body) { - body = JSON.parse(body); - this.auth = body.data; - } - } - - return this.auth; - } - - /** - * Returns a rocketchat config - * @return {Object} Auth config - */ - async function getConfig() { - if (!this.chatConfig) { - const models = Self.app.models; - - this.chatConfig = await models.ChatConfig.findOne(); - } - - return this.chatConfig; - } - - /** - * Send unauthenticated request - * @param {*} uri - Request uri - * @param {*} params - Request params - * @param {*} options - Request options - * - * @return {Object} Request response - */ - async function send(uri, params, options = {}) { - if (process.env.NODE_ENV !== 'production') { + /* if (process.env.NODE_ENV !== 'production') { return new Promise(resolve => { return resolve({ body: JSON.stringify( @@ -118,34 +44,23 @@ module.exports = Self => { }); }); } + */ + const login = await Self.getServiceAuth(); - const defaultOptions = { - form: params - }; + const avatar = `${login.host}/avatar/${sender.name}`; - if (options) Object.assign(defaultOptions, options); - - return got.post(uri, defaultOptions); - } - - /** - * Send authenticated request - * @param {*} uri - Request uri - * @param {*} body - Request params - * - * @return {Object} Request response - */ - async function sendAuth(uri, body) { - const login = await getAuthToken(); const options = { - headers: {} + headers: { + 'X-Auth-Token': login.auth.token, + 'X-User-Id': login.auth.userId + }, }; - if (login) { - options.headers['X-Auth-Token'] = login.authToken; - options.headers['X-User-Id'] = login.userId; - } - - return send(uri, body, options); + return axios.post(`${login.api}/chat.postMessage`, { + 'channel': channel, + 'avatar': avatar, + 'alias': sender.nickname, + 'text': message + }, options); } }; diff --git a/back/methods/chat/sendCheckingPresence.js b/back/methods/chat/sendCheckingPresence.js index fcde20130c..671e8f60f9 100644 --- a/back/methods/chat/sendCheckingPresence.js +++ b/back/methods/chat/sendCheckingPresence.js @@ -1,21 +1,23 @@ +const axios = require('axios'); + module.exports = Self => { Self.remoteMethodCtx('sendCheckingPresence', { description: 'Sends a RocketChat message to a working worker or department channel', accessType: 'WRITE', accepts: [{ - arg: 'workerId', - type: 'Number', + arg: 'recipientId', + type: 'number', required: true, - description: 'The worker id of the destinatary' + description: 'The recipient user id' }, { arg: 'message', - type: 'String', + type: 'string', required: true, description: 'The message' }], returns: { - type: 'Object', + type: 'object', root: true }, http: { @@ -33,30 +35,51 @@ module.exports = Self => { Object.assign(myOptions, options); const models = Self.app.models; - const account = await models.Account.findById(recipientId, null, myOptions); const userId = ctx.req.accessToken.userId; + const recipient = await models.Account.findById(recipientId, null, myOptions); + // Prevent sending messages to yourself if (recipientId == userId) return false; - if (!account) + if (!recipient) throw new Error(`Could not send message "${message}" to worker id ${recipientId} from user ${userId}`); - const query = `SELECT worker_isWorking(?) isWorking`; - const [result] = await Self.rawSql(query, [recipientId], myOptions); + const {data} = await getUserStatus(recipient.name); + if (data) { + if (data.status === 'offline') { + // Send message to department room + const workerDepartment = await models.WorkerDepartment.findById(recipientId, { + include: { + relation: 'department' + } + }, myOptions); + const department = workerDepartment && workerDepartment.department(); + const channelName = department && department.chatName; - if (!result.isWorking) { - const workerDepartment = await models.WorkerDepartment.findById(recipientId, { - include: { - relation: 'department' - } - }, myOptions); - const department = workerDepartment && workerDepartment.department(); - const channelName = department && department.chatName; - - if (channelName) - return Self.send(ctx, `#${channelName}`, `@${account.name} ➔ ${message}`); + if (channelName) + return Self.send(ctx, `#${channelName}`, `@${recipient.name} ➔ ${message}`); + } else + return Self.send(ctx, `@${recipient.name}`, message); } - - return Self.send(ctx, `@${account.name}`, message); }; + + /** + * Returns the current user status on Rocketchat + * + * @param {string} username - The recipient user name + * @return {Promise} - The request promise + */ + async function getUserStatus(username) { + const login = await Self.getServiceAuth(); + + const options = { + params: {username}, + headers: { + 'X-Auth-Token': login.auth.token, + 'X-User-Id': login.auth.userId + }, + }; + + return axios.get(`${login.api}/users.getStatus`, options); + } }; diff --git a/back/models/chat.js b/back/models/chat.js index 5487569c10..7d8468aae8 100644 --- a/back/models/chat.js +++ b/back/models/chat.js @@ -1,4 +1,5 @@ module.exports = Self => { + require('../methods/chat/getServiceAuth')(Self); require('../methods/chat/send')(Self); require('../methods/chat/sendCheckingPresence')(Self); require('../methods/chat/notifyIssues')(Self); From 4e89c66e2ca550c80deaa46183a6ffeef523ffc0 Mon Sep 17 00:00:00 2001 From: alexm Date: Tue, 22 Feb 2022 08:58:22 +0100 Subject: [PATCH 17/31] refactor(client_defaulter): add column date --- e2e/helpers/selectors.js | 10 +++++----- e2e/paths/02-client/21_defaulter.spec.js | 3 ++- front/core/components/smart-table/table.scss | 5 ----- modules/client/front/defaulter/index.html | 21 +++++++++++++++----- modules/client/front/defaulter/locale/es.yml | 8 +++++--- 5 files changed, 28 insertions(+), 19 deletions(-) diff --git a/e2e/helpers/selectors.js b/e2e/helpers/selectors.js index f0a5c37b5f..bb141de8e7 100644 --- a/e2e/helpers/selectors.js +++ b/e2e/helpers/selectors.js @@ -305,11 +305,11 @@ export default { anyCreditInsuranceLine: 'vn-client-credit-insurance-insurance-index vn-tbody > vn-tr', }, clientDefaulter: { - anyClient: 'vn-client-defaulter-index vn-tbody > vn-tr', - firstClientName: 'vn-client-defaulter-index vn-tbody > vn-tr:nth-child(1) > vn-td:nth-child(2) > span', - firstSalesPersonName: 'vn-client-defaulter-index vn-tbody > vn-tr:nth-child(1) > vn-td:nth-child(3) > span', - firstObservation: 'vn-client-defaulter-index vn-tbody > vn-tr:nth-child(1) > vn-td:nth-child(6) > vn-textarea[ng-model="defaulter.observation"]', - allDefaulterCheckbox: 'vn-client-defaulter-index vn-thead vn-multi-check', + anyClient: 'vn-client-defaulter-index tbody > tr', + firstClientName: 'vn-client-defaulter-index tbody > tr:nth-child(1) > td:nth-child(2) > span', + firstSalesPersonName: 'vn-client-defaulter-index tbody > tr:nth-child(1) > td:nth-child(3) > span', + firstObservation: 'vn-client-defaulter-index tbody > tr:nth-child(1) > td:nth-child(6) > vn-textarea[ng-model="defaulter.observation"]', + allDefaulterCheckbox: 'vn-client-defaulter-index thead vn-multi-check', addObservationButton: 'vn-client-defaulter-index vn-button[icon="icon-notes"]', observation: '.vn-dialog.shown vn-textarea[ng-model="$ctrl.defaulter.observation"]', saveButton: 'button[response="accept"]' diff --git a/e2e/paths/02-client/21_defaulter.spec.js b/e2e/paths/02-client/21_defaulter.spec.js index 89b5c5761d..1066776d68 100644 --- a/e2e/paths/02-client/21_defaulter.spec.js +++ b/e2e/paths/02-client/21_defaulter.spec.js @@ -29,7 +29,7 @@ describe('Client defaulter path', () => { await page.waitToGetProperty(selectors.clientDefaulter.firstSalesPersonName, 'innerText'); expect(clientName).toEqual('Ororo Munroe'); - expect(salesPersonName).toEqual('salesPerson'); + expect(salesPersonName).toEqual('salesPersonNick'); }); it('should first observation not changed', async() => { @@ -65,6 +65,7 @@ describe('Client defaulter path', () => { it('should first observation changed', async() => { const message = await page.waitForSnackbar(); + await page.waitForSelector(selectors.clientDefaulter.firstObservation); const result = await page.waitToGetProperty(selectors.clientDefaulter.firstObservation, 'value'); expect(message.text).toContain('Observation saved!'); diff --git a/front/core/components/smart-table/table.scss b/front/core/components/smart-table/table.scss index b40b988a78..c38c149ca3 100644 --- a/front/core/components/smart-table/table.scss +++ b/front/core/components/smart-table/table.scss @@ -99,11 +99,6 @@ smart-table table { } } } - & > td > textarea { - background-color: $color-font-light; - color: $color-font-bg; - width: 90%; - } } .vn-check { margin: 0; diff --git a/modules/client/front/defaulter/index.html b/modules/client/front/defaulter/index.html index 6d723c9759..59f7b7d676 100644 --- a/modules/client/front/defaulter/index.html +++ b/modules/client/front/defaulter/index.html @@ -65,9 +65,15 @@ vn-tooltip="Worker who made the last observation"> Author - + Last observation + + Last observation D. + @@ -111,12 +117,17 @@ {{::defaulter.workerName | dashIfEmpty}} - - + + + + + {{::defaulter.created | date: 'dd/MM/yyyy'}} + {{::defaulter.creditInsurance | currency: 'EUR': 2}} {{::defaulter.defaulterSinced | date: 'dd/MM/yyyy'}} diff --git a/modules/client/front/defaulter/locale/es.yml b/modules/client/front/defaulter/locale/es.yml index 172a3125dc..3f046e8d67 100644 --- a/modules/client/front/defaulter/locale/es.yml +++ b/modules/client/front/defaulter/locale/es.yml @@ -1,7 +1,9 @@ -Last observation: Última observación Add observation: Añadir observación -Search client: Buscar clientes Add observation to all selected clients: Añadir observación a {{total}} cliente(s) seleccionado(s) -Credit I.: Crédito A. Balance D.: Saldo V. +Credit I.: Crédito A. +Last observation: Última observación +Last observation D.: Fecha última O. +Last observation date: Fecha última observación +Search client: Buscar clientes Worker who made the last observation: Trabajador que ha realizado la última observación \ No newline at end of file From 4606b0d7ead878f592edfc68f1a08825acec5d67 Mon Sep 17 00:00:00 2001 From: alexm Date: Tue, 22 Feb 2022 15:23:23 +0100 Subject: [PATCH 18/31] change name for code --- back/methods/docuware/checkFile.js | 2 +- back/methods/docuware/download.js | 2 +- db/changes/10420-valentines/00-docuware.sql | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/back/methods/docuware/checkFile.js b/back/methods/docuware/checkFile.js index a674707fc2..c1af68f152 100644 --- a/back/methods/docuware/checkFile.js +++ b/back/methods/docuware/checkFile.js @@ -43,7 +43,7 @@ module.exports = Self => { const docuwareConfig = await models.DocuwareConfig.findOne(); const docuwareInfo = await models.Docuware.findOne({ where: { - name: fileCabinet, + code: fileCabinet, dialogName: dialog } }); diff --git a/back/methods/docuware/download.js b/back/methods/docuware/download.js index 75789d1878..46b03ce52e 100644 --- a/back/methods/docuware/download.js +++ b/back/methods/docuware/download.js @@ -56,7 +56,7 @@ module.exports = Self => { const docuwareConfig = await models.DocuwareConfig.findOne(); const docuwareInfo = await models.Docuware.findOne({ where: { - name: fileCabinet, + code: fileCabinet, dialogName: dialog } }); diff --git a/db/changes/10420-valentines/00-docuware.sql b/db/changes/10420-valentines/00-docuware.sql index e5311252dd..03b3869770 100644 --- a/db/changes/10420-valentines/00-docuware.sql +++ b/db/changes/10420-valentines/00-docuware.sql @@ -6,6 +6,6 @@ CREATE TABLE `vn`.`docuware` ( `find` varchar(50) DEFAULT NULL ); -INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) +INSERT INTO `vn`.`docuware` (`code`, `fileCabinetName`, `dialogName` , `find`) VALUES ('deliveryClient', 'Albaranes cliente', 'findTicket', 'N__ALBAR_N'); \ No newline at end of file From f3ff64c44df2a5b99d86a80c5a8c8e7b55ebaab1 Mon Sep 17 00:00:00 2001 From: alexm Date: Wed, 23 Feb 2022 08:11:54 +0100 Subject: [PATCH 19/31] refactor(docuware): name for code --- back/models/docuware.json | 2 +- db/changes/10420-valentines/00-docuware.sql | 2 +- db/dump/fixtures.sql | 8 ++++++-- 3 files changed, 8 insertions(+), 4 deletions(-) diff --git a/back/models/docuware.json b/back/models/docuware.json index f853970722..fb2ed919ea 100644 --- a/back/models/docuware.json +++ b/back/models/docuware.json @@ -13,7 +13,7 @@ "id": true, "description": "Identifier" }, - "name": { + "code": { "type": "string" }, "fileCabinetName": { diff --git a/db/changes/10420-valentines/00-docuware.sql b/db/changes/10420-valentines/00-docuware.sql index 03b3869770..7cabd135f8 100644 --- a/db/changes/10420-valentines/00-docuware.sql +++ b/db/changes/10420-valentines/00-docuware.sql @@ -1,6 +1,6 @@ CREATE TABLE `vn`.`docuware` ( `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY, - `name` varchar(50) NULL, + `code` varchar(50) NULL, `fileCabinetName` varchar(50) NULL, `dialogName` varchar(255) DEFAULT NULL, `find` varchar(50) DEFAULT NULL diff --git a/db/dump/fixtures.sql b/db/dump/fixtures.sql index 74568ebc72..20298677a5 100644 --- a/db/dump/fixtures.sql +++ b/db/dump/fixtures.sql @@ -2444,6 +2444,10 @@ INSERT INTO `bs`.`defaulter` (`clientFk`, `amount`, `created`, `defaulterSinced` (1107, 500, CURDATE(), CURDATE()), (1109, 500, CURDATE(), CURDATE()); -INSERT INTO `vn`.`docuware` (`name`, `fileCabinetName`, `dialogName` , `find`) +INSERT INTO `vn`.`docuware` (`code`, `fileCabinetName`, `dialogName` , `find`) VALUES - ('deliveryClientTest', 'deliveryClientTest', 'findTest', 'word'); \ No newline at end of file + ('deliveryClientTest', 'deliveryClientTest', 'findTest', 'word'); + +INSERT INTO `vn`.`docuwareConfig` (`url`) + VALUES + ('https://verdnatura.docuware.cloud/docuware/platform'); \ No newline at end of file From 8a8951b8b0a0dcb46bd2688cf5f665c9b4e3d375 Mon Sep 17 00:00:00 2001 From: alexm Date: Wed, 23 Feb 2022 08:53:25 +0100 Subject: [PATCH 20/31] feat(client_defaulter): add columns to search --- modules/client/front/defaulter/index.js | 12 +++--------- 1 file changed, 3 insertions(+), 9 deletions(-) diff --git a/modules/client/front/defaulter/index.js b/modules/client/front/defaulter/index.js index 434ae9cb62..f4071108cf 100644 --- a/modules/client/front/defaulter/index.js +++ b/modules/client/front/defaulter/index.js @@ -30,10 +30,6 @@ export default class Controller extends Section { valueField: 'id', } }, - { - field: 'amount', - searchable: false - }, { field: 'workerFk', autocomplete: { @@ -52,10 +48,6 @@ export default class Controller extends Section { valueField: 'observation', } }, - { - field: 'creditInsurance', - searchable: false - }, { field: 'defaulterSinced', searchable: false @@ -122,7 +114,9 @@ export default class Controller extends Section { exprBuilder(param, value) { switch (param) { case 'observation': - return {[`observation`]: value}; + return {[`observation`]: {like: `%${value}%`}}; + case 'creditInsurance': + case 'amount': case 'clientName': case 'workerFk': case 'salesPersonFk': From a5614e5d5dbd0f363d9e7a6368a313ea687a1720 Mon Sep 17 00:00:00 2001 From: alexm Date: Wed, 23 Feb 2022 09:52:45 +0100 Subject: [PATCH 21/31] change client.name for client.socialName --- e2e/paths/02-client/21_defaulter.spec.js | 2 +- modules/client/back/methods/defaulter/filter.js | 2 +- .../client/back/methods/defaulter/specs/filter.spec.js | 4 ++-- modules/client/front/defaulter/index.js | 9 ++++++--- 4 files changed, 10 insertions(+), 7 deletions(-) diff --git a/e2e/paths/02-client/21_defaulter.spec.js b/e2e/paths/02-client/21_defaulter.spec.js index 1066776d68..3630a958ae 100644 --- a/e2e/paths/02-client/21_defaulter.spec.js +++ b/e2e/paths/02-client/21_defaulter.spec.js @@ -28,7 +28,7 @@ describe('Client defaulter path', () => { const salesPersonName = await page.waitToGetProperty(selectors.clientDefaulter.firstSalesPersonName, 'innerText'); - expect(clientName).toEqual('Ororo Munroe'); + expect(clientName).toEqual('Batman'); expect(salesPersonName).toEqual('salesPersonNick'); }); diff --git a/modules/client/back/methods/defaulter/filter.js b/modules/client/back/methods/defaulter/filter.js index 0a1d5093b9..c65991273e 100644 --- a/modules/client/back/methods/defaulter/filter.js +++ b/modules/client/back/methods/defaulter/filter.js @@ -56,7 +56,7 @@ module.exports = Self => { FROM ( SELECT DISTINCT c.id clientFk, - c.name clientName, + c.socialName clientName, c.salesPersonFk, u.nickname salesPersonName, d.amount, diff --git a/modules/client/back/methods/defaulter/specs/filter.spec.js b/modules/client/back/methods/defaulter/specs/filter.spec.js index 145bb51321..ca14d1e437 100644 --- a/modules/client/back/methods/defaulter/specs/filter.spec.js +++ b/modules/client/back/methods/defaulter/specs/filter.spec.js @@ -47,12 +47,12 @@ describe('defaulter filter()', () => { try { const options = {transaction: tx}; - const ctx = {req: {accessToken: {userId: authUserId}}, args: {search: 'bruce'}}; + const ctx = {req: {accessToken: {userId: authUserId}}, args: {search: 'spider'}}; const result = await models.Defaulter.filter(ctx, null, options); const firstRow = result[0]; - expect(firstRow.clientName).toEqual('Bruce Wayne'); + expect(firstRow.clientName).toEqual('Spider man'); await tx.rollback(); } catch (e) { diff --git a/modules/client/front/defaulter/index.js b/modules/client/front/defaulter/index.js index f4071108cf..5fcc955ccf 100644 --- a/modules/client/front/defaulter/index.js +++ b/modules/client/front/defaulter/index.js @@ -16,8 +16,8 @@ export default class Controller extends Section { field: 'clientName', autocomplete: { url: 'Clients', - showField: 'name', - valueField: 'name' + showField: 'socialName', + valueField: 'socialName' } }, { @@ -34,7 +34,6 @@ export default class Controller extends Section { field: 'workerFk', autocomplete: { url: 'Workers/activeWithInheritedRole', - where: `{role: 'salesPerson'}`, searchFunction: '{firstName: $search}', showField: 'nickname', valueField: 'id', @@ -48,6 +47,10 @@ export default class Controller extends Section { valueField: 'observation', } }, + { + field: 'created', + searchable: false + }, { field: 'defaulterSinced', searchable: false From 9d298c2a5eb8a7159ed51c299b1c113e57a3f3e0 Mon Sep 17 00:00:00 2001 From: joan Date: Wed, 23 Feb 2022 12:07:05 +0100 Subject: [PATCH 22/31] Updated unit tests --- back/methods/chat/send.js | 10 ++-- back/methods/chat/sendCheckingPresence.js | 16 ++++- .../chat/spec/sendCheckingPresence.spec.js | 60 ++++++++++++------- .../claim/specs/createFromSales.spec.js | 4 +- .../client/specs/updateFiscalData.spec.js | 2 +- 5 files changed, 58 insertions(+), 34 deletions(-) diff --git a/back/methods/chat/send.js b/back/methods/chat/send.js index 5f79449456..67e0dbb87d 100644 --- a/back/methods/chat/send.js +++ b/back/methods/chat/send.js @@ -35,18 +35,16 @@ module.exports = Self => { }; async function sendMessage(sender, channel, message) { - /* if (process.env.NODE_ENV !== 'production') { + if (process.env.NODE_ENV !== 'production') { return new Promise(resolve => { return resolve({ - body: JSON.stringify( - {statusCode: 200, message: 'Fake notification sent'} - ) + statusCode: 200, + message: 'Fake notification sent' }); }); } - */ - const login = await Self.getServiceAuth(); + const login = await Self.getServiceAuth(); const avatar = `${login.host}/avatar/${sender.name}`; const options = { diff --git a/back/methods/chat/sendCheckingPresence.js b/back/methods/chat/sendCheckingPresence.js index 671e8f60f9..10a98452f9 100644 --- a/back/methods/chat/sendCheckingPresence.js +++ b/back/methods/chat/sendCheckingPresence.js @@ -44,7 +44,7 @@ module.exports = Self => { if (!recipient) throw new Error(`Could not send message "${message}" to worker id ${recipientId} from user ${userId}`); - const {data} = await getUserStatus(recipient.name); + const {data} = await Self.getUserStatus(recipient.name); if (data) { if (data.status === 'offline') { // Send message to department room @@ -69,7 +69,17 @@ module.exports = Self => { * @param {string} username - The recipient user name * @return {Promise} - The request promise */ - async function getUserStatus(username) { + Self.getUserStatus = async function getUserStatus(username) { + if (process.env.NODE_ENV !== 'production') { + return new Promise(resolve => { + return resolve({ + data: { + status: 'online' + } + }); + }); + } + const login = await Self.getServiceAuth(); const options = { @@ -81,5 +91,5 @@ module.exports = Self => { }; return axios.get(`${login.api}/users.getStatus`, options); - } + }; }; diff --git a/back/methods/chat/spec/sendCheckingPresence.spec.js b/back/methods/chat/spec/sendCheckingPresence.spec.js index e9c61fd21f..2c48ef02ca 100644 --- a/back/methods/chat/spec/sendCheckingPresence.spec.js +++ b/back/methods/chat/spec/sendCheckingPresence.spec.js @@ -1,46 +1,62 @@ -const app = require('vn-loopback/server/server'); +const models = require('vn-loopback/server/server').models; describe('Chat sendCheckingPresence()', () => { const today = new Date(); today.setHours(6, 0); const ctx = {req: {accessToken: {userId: 1}}}; - const chatModel = app.models.Chat; + const chatModel = models.Chat; const departmentId = 23; const workerId = 1107; - it(`should call send() method with the worker name if he's currently working then return a response`, async() => { + it(`should call to send() method with "@HankPym" as recipient argument`, async() => { spyOn(chatModel, 'send').and.callThrough(); - - const timeEntry = await app.models.WorkerTimeControl.create({ - userFk: workerId, - timed: today, - manual: false, - direction: 'in' - }); + spyOn(chatModel, 'getUserStatus').and.returnValue( + new Promise(resolve => { + return resolve({ + data: { + status: 'online' + } + }); + }) + ); const response = await chatModel.sendCheckingPresence(ctx, workerId, 'I changed something'); expect(response.statusCode).toEqual(200); expect(response.message).toEqual('Fake notification sent'); expect(chatModel.send).toHaveBeenCalledWith(ctx, '@HankPym', 'I changed something'); - - // restores - await app.models.WorkerTimeControl.destroyById(timeEntry.id); }); - it(`should call to send() method with the worker department channel if he's not currently working then return a response`, async() => { + it(`should call to send() method with "#cooler" as recipient argument`, async() => { spyOn(chatModel, 'send').and.callThrough(); + spyOn(chatModel, 'getUserStatus').and.returnValue( + new Promise(resolve => { + return resolve({ + data: { + status: 'offline' + } + }); + }) + ); - const department = await app.models.Department.findById(departmentId); - await department.updateAttribute('chatName', 'cooler'); + const tx = await models.Claim.beginTransaction({}); - const response = await chatModel.sendCheckingPresence(ctx, workerId, 'I changed something'); + try { + const options = {transaction: tx}; - expect(response.statusCode).toEqual(200); - expect(response.message).toEqual('Fake notification sent'); - expect(chatModel.send).toHaveBeenCalledWith(ctx, '#cooler', '@HankPym ➔ I changed something'); + const department = await models.Department.findById(departmentId, null, options); + await department.updateAttribute('chatName', 'cooler'); - // restores - await department.updateAttribute('chatName', null); + const response = await chatModel.sendCheckingPresence(ctx, workerId, 'I changed something'); + + expect(response.statusCode).toEqual(200); + expect(response.message).toEqual('Fake notification sent'); + expect(chatModel.send).toHaveBeenCalledWith(ctx, '#cooler', '@HankPym ➔ I changed something'); + + await tx.rollback(); + } catch (e) { + await tx.rollback(); + throw e; + } }); }); diff --git a/modules/claim/back/methods/claim/specs/createFromSales.spec.js b/modules/claim/back/methods/claim/specs/createFromSales.spec.js index 097dcc0d92..9151c361e0 100644 --- a/modules/claim/back/methods/claim/specs/createFromSales.spec.js +++ b/modules/claim/back/methods/claim/specs/createFromSales.spec.js @@ -57,7 +57,7 @@ describe('Claim createFromSales()', () => { const todayMinusEightDays = new Date(); todayMinusEightDays.setDate(todayMinusEightDays.getDate() - 8); - const ticket = await models.Ticket.findById(ticketId, options); + const ticket = await models.Ticket.findById(ticketId, null, options); await ticket.updateAttribute('landed', todayMinusEightDays, options); const claim = await models.Claim.createFromSales(ctx, ticketId, newSale, options); @@ -88,7 +88,7 @@ describe('Claim createFromSales()', () => { const todayMinusEightDays = new Date(); todayMinusEightDays.setDate(todayMinusEightDays.getDate() - 8); - const ticket = await models.Ticket.findById(ticketId, options); + const ticket = await models.Ticket.findById(ticketId, null, options); await ticket.updateAttribute('landed', todayMinusEightDays, options); await models.Claim.createFromSales(ctx, ticketId, newSale, options); diff --git a/modules/client/back/methods/client/specs/updateFiscalData.spec.js b/modules/client/back/methods/client/specs/updateFiscalData.spec.js index 75273a39ff..7c0bc05998 100644 --- a/modules/client/back/methods/client/specs/updateFiscalData.spec.js +++ b/modules/client/back/methods/client/specs/updateFiscalData.spec.js @@ -35,7 +35,7 @@ describe('Client updateFiscalData', () => { try { const options = {transaction: tx}; - const client = await models.Client.findById(clientId, options); + const client = await models.Client.findById(clientId, null, options); await client.updateAttribute('isTaxDataChecked', false, options); const ctx = {req: {accessToken: {userId: salesAssistantId}}}; From 9ba13f90d35d541eda7ba1fb22ca718b64827ee0 Mon Sep 17 00:00:00 2001 From: carlosjr Date: Wed, 23 Feb 2022 16:12:29 +0100 Subject: [PATCH 23/31] #3015 feat(unlink): tickets link to route can now be removed from the suggested tickets to route --- .../back/methods/route/getSuggestedTickets.js | 7 ++++ .../back/methods/route/specs/unlink.spec.js | 33 +++++++++++++++ modules/route/back/methods/route/unlink.js | 42 +++++++++++++++++++ modules/route/back/models/route.js | 1 + modules/route/front/tickets/index.html | 20 ++++++++- modules/route/front/tickets/index.js | 13 ++++++ modules/route/front/tickets/index.spec.js | 27 ++++++++++++ modules/route/front/tickets/locale/es.yml | 3 +- modules/zone/back/models/agency.json | 4 +- modules/zone/back/models/zone.json | 16 +++---- 10 files changed, 153 insertions(+), 13 deletions(-) create mode 100644 modules/route/back/methods/route/specs/unlink.spec.js create mode 100644 modules/route/back/methods/route/unlink.js diff --git a/modules/route/back/methods/route/getSuggestedTickets.js b/modules/route/back/methods/route/getSuggestedTickets.js index c1d6b67fe9..f0333e66bf 100644 --- a/modules/route/back/methods/route/getSuggestedTickets.js +++ b/modules/route/back/methods/route/getSuggestedTickets.js @@ -25,6 +25,7 @@ module.exports = Self => { Object.assign(myOptions, options); const route = await Self.app.models.Route.findById(id, null, myOptions); + const zoneAgencyModes = await Self.app.models.ZoneAgencyMode.find({ where: { agencyModeFk: route.agencyModeFk @@ -52,6 +53,12 @@ module.exports = Self => { fields: ['id', 'name'] } }, + { + relation: 'zone', + scope: { + fields: ['id', 'name'] + } + }, { relation: 'address', scope: { diff --git a/modules/route/back/methods/route/specs/unlink.spec.js b/modules/route/back/methods/route/specs/unlink.spec.js new file mode 100644 index 0000000000..808cedccc1 --- /dev/null +++ b/modules/route/back/methods/route/specs/unlink.spec.js @@ -0,0 +1,33 @@ +const models = require('vn-loopback/server/server').models; + +describe('route unlink()', () => { + it('should show no tickets since the link between zone and route for the give agencymode was removed', async() => { + const tx = await models.ZoneAgencyMode.beginTransaction({}); + const agencyModeId = 1; + const zoneId = 1; + routeId = 1; + + try { + const options = {transaction: tx}; + + let zoneAgencyModes = await models.ZoneAgencyMode.find(null, options); + let tickets = await models.Route.getSuggestedTickets(routeId, options); + + expect(zoneAgencyModes.length).toEqual(4); + expect(tickets.length).toEqual(3); + + await models.Route.unlink(agencyModeId, zoneId, options); + + zoneAgencyModes = await models.ZoneAgencyMode.find(null, options); + tickets = await models.Route.getSuggestedTickets(routeId, options); + + expect(zoneAgencyModes.length).toEqual(3); + expect(tickets.length).toEqual(0); + + await tx.rollback(); + } catch (e) { + await tx.rollback(); + throw e; + } + }); +}); diff --git a/modules/route/back/methods/route/unlink.js b/modules/route/back/methods/route/unlink.js new file mode 100644 index 0000000000..5a847e3377 --- /dev/null +++ b/modules/route/back/methods/route/unlink.js @@ -0,0 +1,42 @@ +module.exports = Self => { + Self.remoteMethod('unlink', { + description: 'Removes the matching entries from zoneAgencyMode', + accessType: 'WRITE', + accepts: [ + { + arg: 'agencyModeId', + type: 'number', + required: true, + description: 'The agencyMode id', + }, + { + arg: 'zoneId', + type: 'number', + required: true, + description: 'The zone id', + }, + ], + returns: { + type: ['object'], + root: true + }, + http: { + path: `/unlink`, + verb: 'POST' + } + }); + + Self.unlink = async(agencyModeId, zoneId, options) => { + const myOptions = {}; + + if (typeof options == 'object') + Object.assign(myOptions, options); + + const where = { + agencyModeFk: agencyModeId, + zoneFk: zoneId + }; + + await Self.app.models.ZoneAgencyMode.destroyAll(where, myOptions); + }; +}; diff --git a/modules/route/back/models/route.js b/modules/route/back/models/route.js index 1cfe0927e0..c82d1722e9 100644 --- a/modules/route/back/models/route.js +++ b/modules/route/back/models/route.js @@ -8,6 +8,7 @@ module.exports = Self => { require('../methods/route/insertTicket')(Self); require('../methods/route/clone')(Self); require('../methods/route/getSuggestedTickets')(Self); + require('../methods/route/unlink')(Self); Self.validate('kmStart', validateDistance, { message: 'Distance must be lesser than 1000' diff --git a/modules/route/front/tickets/index.html b/modules/route/front/tickets/index.html index 7d515b67cf..970c7574bc 100644 --- a/modules/route/front/tickets/index.html +++ b/modules/route/front/tickets/index.html @@ -150,7 +150,7 @@ PC Address - Warehouse + Zone
@@ -174,7 +174,15 @@ {{::ticket.address.city}} {{::ticket.address.postalCode}} {{::ticket.address.street}} - {{::ticket.warehouse.name}} + + {{::ticket.zone.name}} + + + @@ -196,3 +204,11 @@ + + + + \ No newline at end of file diff --git a/modules/route/front/tickets/index.js b/modules/route/front/tickets/index.js index fd763e32f8..e74cbcd409 100644 --- a/modules/route/front/tickets/index.js +++ b/modules/route/front/tickets/index.js @@ -37,6 +37,19 @@ class Controller extends Section { }); } + unlinkZone(ticket) { + const params = { + agencyModeId: this.route.agencyModeFk, + zoneId: ticket.zoneFk, + }; + + const query = `Routes/unlink`; + this.$http.post(query, params).then(() => { + this.vnApp.showSuccess(this.$t('Data saved!')); + this.$.possibleTicketsModel.refresh(); + }); + } + getSelectedItems(items) { const selectedItems = []; diff --git a/modules/route/front/tickets/index.spec.js b/modules/route/front/tickets/index.spec.js index fbbe943600..092445e6f6 100644 --- a/modules/route/front/tickets/index.spec.js +++ b/modules/route/front/tickets/index.spec.js @@ -1,3 +1,4 @@ +/* eslint max-len: ["error", { "code": 150 }]*/ import './index'; describe('Route', () => { @@ -73,6 +74,32 @@ describe('Route', () => { }); }); + describe('unlink()', () => { + it('should call the route unlink endpoint with the agency and zone ids', () => { + controller.$.possibleTicketsModel = {refresh: jest.fn()}; + jest.spyOn(controller.vnApp, 'showSuccess'); + + controller.route = { + agencyModeFk: 1 + }; + + const ticket = { + zoneFk: 2, + }; + const params = { + agencyModeId: controller.route.agencyModeFk, + zoneId: ticket.zoneFk, + }; + + $httpBackend.expectPOST(`Routes/unlink`, params).respond('ok'); + controller.unlinkZone(ticket); + $httpBackend.flush(); + + expect(controller.vnApp.showSuccess).toHaveBeenCalled(); + expect(controller.$.possibleTicketsModel.refresh).toHaveBeenCalledWith(); + }); + }); + describe('getSelectedItems()', () => { it('should return the selected items', () => { let items = [ diff --git a/modules/route/front/tickets/locale/es.yml b/modules/route/front/tickets/locale/es.yml index c38d4115c3..6d63b4b6e4 100644 --- a/modules/route/front/tickets/locale/es.yml +++ b/modules/route/front/tickets/locale/es.yml @@ -11,4 +11,5 @@ The selected ticket is not suitable for this route: El ticket seleccionado no es PC: CP The route's vehicle doesn't have a delivery point: El vehículo de la ruta no tiene un punto de entrega The route doesn't have a vehicle: La ruta no tiene un vehículo -Population: Población \ No newline at end of file +Population: Población +Unlink selected zone?: Desvincular zona seleccionada? diff --git a/modules/zone/back/models/agency.json b/modules/zone/back/models/agency.json index 9269b3db64..edec36f874 100644 --- a/modules/zone/back/models/agency.json +++ b/modules/zone/back/models/agency.json @@ -9,11 +9,11 @@ "properties": { "id": { "id": true, - "type": "Number", + "type": "number", "forceId": false }, "name": { - "type": "String", + "type": "string", "required": false } } diff --git a/modules/zone/back/models/zone.json b/modules/zone/back/models/zone.json index ad43bd6f6e..5d5970173a 100644 --- a/modules/zone/back/models/zone.json +++ b/modules/zone/back/models/zone.json @@ -13,10 +13,10 @@ "properties": { "id": { "id": true, - "type": "Number" + "type": "number" }, "name": { - "type": "String", + "type": "string", "required": true }, "hour": { @@ -24,22 +24,22 @@ "required": true }, "travelingDays": { - "type": "Number" + "type": "number" }, "price": { - "type": "Number" + "type": "number" }, "bonus": { - "type": "Number" + "type": "number" }, "isVolumetric": { - "type": "Boolean" + "type": "boolean" }, "inflation": { - "type": "Number" + "type": "number" }, "itemMaxSize": { - "type": "Number" + "type": "number" } }, "relations": { From c3e480b2e7832d49aab4ed9de8acfbd823db2260 Mon Sep 17 00:00:00 2001 From: Juan Ferrer Toribio Date: Thu, 24 Feb 2022 15:02:16 +0100 Subject: [PATCH 24/31] MariaDB user sync disabled in dev environment --- modules/account/back/models/role-config.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/modules/account/back/models/role-config.js b/modules/account/back/models/role-config.js index c6b32a4c5a..6051f2060a 100644 --- a/modules/account/back/models/role-config.js +++ b/modules/account/back/models/role-config.js @@ -1,6 +1,10 @@ module.exports = Self => { Self.getSynchronizer = async function() { + let NODE_ENV = process.env.NODE_ENV; + if (!NODE_ENV || NODE_ENV == 'development') + return null; + return await Self.findOne({ fields: ['id', 'rolePrefix', 'userPrefix', 'userHost'] }); From bf0734ca67deb114627f8c32544823ee74552f3d Mon Sep 17 00:00:00 2001 From: carlosjr Date: Mon, 28 Feb 2022 10:46:14 +0100 Subject: [PATCH 25/31] excluded 3 test suites until db export --- modules/client/back/methods/client/specs/sendSms.spec.js | 3 ++- modules/client/back/methods/sms/send.spec.js | 3 ++- modules/ticket/back/methods/ticket/specs/sendSms.spec.js | 3 ++- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/modules/client/back/methods/client/specs/sendSms.spec.js b/modules/client/back/methods/client/specs/sendSms.spec.js index 121d427cee..54fe802e3b 100644 --- a/modules/client/back/methods/client/specs/sendSms.spec.js +++ b/modules/client/back/methods/client/specs/sendSms.spec.js @@ -1,7 +1,8 @@ const models = require('vn-loopback/server/server').models; const soap = require('soap'); -describe('client sendSms()', () => { +// #3673 sendSms tests excluded +xdescribe('client sendSms()', () => { it('should now send a message and log it', async() => { spyOn(soap, 'createClientAsync').and.returnValue('a so fake client'); const tx = await models.Client.beginTransaction({}); diff --git a/modules/client/back/methods/sms/send.spec.js b/modules/client/back/methods/sms/send.spec.js index 7ca78b2149..a81c24e96d 100644 --- a/modules/client/back/methods/sms/send.spec.js +++ b/modules/client/back/methods/sms/send.spec.js @@ -1,6 +1,7 @@ const app = require('vn-loopback/server/server'); -describe('sms send()', () => { +// #3673 sendSms tests excluded +xdescribe('sms send()', () => { it('should not return status error', async() => { const ctx = {req: {accessToken: {userId: 1}}}; const result = await app.models.Sms.send(ctx, 1105, '123456789', 'My SMS Body'); diff --git a/modules/ticket/back/methods/ticket/specs/sendSms.spec.js b/modules/ticket/back/methods/ticket/specs/sendSms.spec.js index 8ec4ca487a..46ae23702b 100644 --- a/modules/ticket/back/methods/ticket/specs/sendSms.spec.js +++ b/modules/ticket/back/methods/ticket/specs/sendSms.spec.js @@ -1,7 +1,8 @@ const models = require('vn-loopback/server/server').models; const soap = require('soap'); -describe('ticket sendSms()', () => { +// #3673 sendSms tests excluded +xdescribe('ticket sendSms()', () => { it('should send a message and log it', async() => { const tx = await models.Ticket.beginTransaction({}); From 4b963804c61b5c420153c740c6cd2423d8d9096b Mon Sep 17 00:00:00 2001 From: carlosjr Date: Mon, 28 Feb 2022 10:54:32 +0100 Subject: [PATCH 26/31] added transalation to item waste --- modules/item/front/waste/locale/es.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/modules/item/front/waste/locale/es.yml b/modules/item/front/waste/locale/es.yml index 9f08e3a724..b9cd33dec6 100644 --- a/modules/item/front/waste/locale/es.yml +++ b/modules/item/front/waste/locale/es.yml @@ -1,3 +1,4 @@ Family: Familia Percentage: Porcentaje -Dwindle: Mermas \ No newline at end of file +Dwindle: Mermas +Minimize/Maximize: Minimizar/Maximizar \ No newline at end of file From cf9851c8dc380229564a548259d51b2ba45f3ac7 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 28 Feb 2022 13:27:03 +0100 Subject: [PATCH 27/31] typo --- back/methods/docuware/checkFile.js | 4 ++-- back/methods/docuware/download.js | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/back/methods/docuware/checkFile.js b/back/methods/docuware/checkFile.js index c1af68f152..c6712bb658 100644 --- a/back/methods/docuware/checkFile.js +++ b/back/methods/docuware/checkFile.js @@ -59,7 +59,7 @@ module.exports = Self => { 'Cookie': cookie } }; - const condtions = { + const searchFilter = { condition: [ { DBName: find, @@ -80,7 +80,7 @@ module.exports = Self => { const dialogId = dialogJson.find(dialogs => dialogs.DisplayName === 'find').Id; // get docuwareID - Object.assign(options, {'body': JSON.stringify(condtions)}); + Object.assign(options, {'body': JSON.stringify(searchFilter)}); const response = await got.post( `${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, options); JSON.parse(response.body).Items[0].Id; diff --git a/back/methods/docuware/download.js b/back/methods/docuware/download.js index 46b03ce52e..489a07e343 100644 --- a/back/methods/docuware/download.js +++ b/back/methods/docuware/download.js @@ -72,7 +72,7 @@ module.exports = Self => { 'Cookie': cookie } }; - const condtions = { + const searchFilter = { condition: [ { DBName: find, @@ -93,7 +93,7 @@ module.exports = Self => { const dialogId = dialogJson.find(dialogs => dialogs.DisplayName === 'find').Id; // get docuwareID - Object.assign(options, {'body': JSON.stringify(condtions)}); + Object.assign(options, {'body': JSON.stringify(searchFilter)}); const response = await got.post(`${docuwareUrl}/FileCabinets/${fileCabinetId}/Query/DialogExpression?dialogId=${dialogId}`, options); const docuwareId = JSON.parse(response.body).Items[0].Id; From 4046617eab70394d0d0d740007fad76679e07742 Mon Sep 17 00:00:00 2001 From: alexm Date: Mon, 28 Feb 2022 13:37:44 +0100 Subject: [PATCH 28/31] short form --- modules/ticket/front/descriptor-menu/index.js | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/modules/ticket/front/descriptor-menu/index.js b/modules/ticket/front/descriptor-menu/index.js index 4304d85239..841dfa4099 100644 --- a/modules/ticket/front/descriptor-menu/index.js +++ b/modules/ticket/front/descriptor-menu/index.js @@ -129,9 +129,7 @@ class Controller extends Section { dialog: 'findTicket' }; this.$http.post(`Docuwares/${this.id}/checkFile`, params) - .then(res => { - this.hasDocuwareFile = res.data; - }); + .then(res => this.hasDocuwareFile = res.data); } showCsvDeliveryNote() { From 3512e287ae0070991c66cf37fb4f54b6a3e60b1e Mon Sep 17 00:00:00 2001 From: joan Date: Tue, 1 Mar 2022 11:09:10 +0100 Subject: [PATCH 29/31] Updated endpoints description --- back/methods/chat/getServiceAuth.js | 2 +- back/methods/chat/sendCheckingPresence.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/back/methods/chat/getServiceAuth.js b/back/methods/chat/getServiceAuth.js index 7eb0ceaa54..8270921090 100644 --- a/back/methods/chat/getServiceAuth.js +++ b/back/methods/chat/getServiceAuth.js @@ -2,7 +2,7 @@ const axios = require('axios'); const tokenLifespan = 10; module.exports = Self => { Self.remoteMethodCtx('getServiceAuth', { - description: 'Send a RocketChat message', + description: 'Authenticates with the service and request a new token', accessType: 'READ', accepts: [], returns: { diff --git a/back/methods/chat/sendCheckingPresence.js b/back/methods/chat/sendCheckingPresence.js index 10a98452f9..429ecdab01 100644 --- a/back/methods/chat/sendCheckingPresence.js +++ b/back/methods/chat/sendCheckingPresence.js @@ -2,7 +2,7 @@ const axios = require('axios'); module.exports = Self => { Self.remoteMethodCtx('sendCheckingPresence', { - description: 'Sends a RocketChat message to a working worker or department channel', + description: 'Sends a RocketChat message to a connected user or department channel', accessType: 'WRITE', accepts: [{ arg: 'recipientId', From 2026e909e93e0ff76e2d70b278c65f0855360fab Mon Sep 17 00:00:00 2001 From: alexm Date: Tue, 1 Mar 2022 11:43:35 +0100 Subject: [PATCH 30/31] disable search observation --- modules/client/back/methods/defaulter/filter.js | 2 +- modules/client/front/defaulter/index.js | 8 +------- 2 files changed, 2 insertions(+), 8 deletions(-) diff --git a/modules/client/back/methods/defaulter/filter.js b/modules/client/back/methods/defaulter/filter.js index c65991273e..095b9b1c17 100644 --- a/modules/client/back/methods/defaulter/filter.js +++ b/modules/client/back/methods/defaulter/filter.js @@ -61,7 +61,7 @@ module.exports = Self => { u.nickname salesPersonName, d.amount, co.created, - CONCAT(DATE(co.created), ' ', co.text) observation, + co.text observation, uw.id workerFk, uw.nickname workerName, c.creditInsurance, diff --git a/modules/client/front/defaulter/index.js b/modules/client/front/defaulter/index.js index 5fcc955ccf..9595be61c7 100644 --- a/modules/client/front/defaulter/index.js +++ b/modules/client/front/defaulter/index.js @@ -41,11 +41,7 @@ export default class Controller extends Section { }, { field: 'observation', - autocomplete: { - url: 'Defaulters/filter', - showField: 'observation', - valueField: 'observation', - } + searchable: false }, { field: 'created', @@ -116,8 +112,6 @@ export default class Controller extends Section { exprBuilder(param, value) { switch (param) { - case 'observation': - return {[`observation`]: {like: `%${value}%`}}; case 'creditInsurance': case 'amount': case 'clientName': From cb21a510650e66417c35f6770f56357f1200e848 Mon Sep 17 00:00:00 2001 From: joan Date: Tue, 1 Mar 2022 12:12:40 +0100 Subject: [PATCH 31/31] Added SQL version 10430-ash --- db/changes/10430-ash/delete.keep | 1 + 1 file changed, 1 insertion(+) create mode 100644 db/changes/10430-ash/delete.keep diff --git a/db/changes/10430-ash/delete.keep b/db/changes/10430-ash/delete.keep new file mode 100644 index 0000000000..8fe7322e3d --- /dev/null +++ b/db/changes/10430-ash/delete.keep @@ -0,0 +1 @@ +delete file \ No newline at end of file