#7897 - masterTest_24_36 #2909

Merged
jsegarra merged 132 commits from 7897_masterTest_24_36 into master 2024-09-03 06:37:54 +00:00
420 changed files with 2738 additions and 15195 deletions
Showing only changes of commit 79e2424a41 - Show all commits

View File

@ -30,17 +30,8 @@ module.exports = Self => {
// Schedule to remove current token
setTimeout(async() => {
let exists;
try {
exists = await models.AccessToken.findById(token.id);
exists && await Self.logout(token.id);
} catch (error) {
// eslint-disable-next-line no-console
console.error(error);
const body = {error: error.message, now: Date.now(), userId: token?.userId ?? null, exists};
await handleError(body);
throw new Error(error);
}
if (await models.AccessToken.findById(token.id))
await Self.logout(token.id);
}, courtesyTime * 1000);
// Get scopes
@ -53,14 +44,20 @@ module.exports = Self => {
return {id: accessToken.id, ttl: accessToken.ttl};
} catch (error) {
const body = {error: error.message, now: Date.now(), userId: token?.userId ?? null, createTokenOptions, isNotExceeded};
await handleError(body);
const body = {
error: error.message,
userId: token?.userId ?? null,
token: token?.id,
scopes: token?.scopes,
createTokenOptions,
isNotExceeded
};
await handleError(JSON.stringify(body));
throw new Error(error);
}
};
};
async function handleError(body, tag = 'renewToken') {
body = JSON.stringify(body);
await models.Application.rawSql('CALL util.debugAdd(?,?);', [tag, body]);
async function handleError(body) {
await models.Application.rawSql('CALL util.debugAdd(?,?);', ['renewToken', body]);
}

View File

@ -67,7 +67,9 @@ module.exports = Self => {
if (vnUser.twoFactor === 'email') {
const $ = Self.app.models;
const code = String(Math.floor(Math.random() * 999999));
const min = 100000;
const max = 999999;
const code = String(Math.floor(Math.random() * (max - min + 1)) + min);
const maxTTL = ((60 * 1000) * 5); // 5 min
await $.AuthCode.upsertWithWhere({userFk: vnUser.id}, {
userFk: vnUser.id,

View File

@ -24,6 +24,10 @@ module.exports = Self => {
arg: 'lang',
type: 'string',
description: 'The user lang'
}, {
arg: 'twoFactor',
type: 'string',
description: 'The user twoFactor'
}
],
http: {
@ -32,8 +36,8 @@ module.exports = Self => {
}
});
Self.updateUser = async(ctx, id, name, nickname, email, lang) => {
Self.updateUser = async(ctx, id, name, nickname, email, lang, twoFactor) => {
await Self.userSecurity(ctx, id);
await Self.upsertWithWhere({id}, {name, nickname, email, lang});
await Self.upsertWithWhere({id}, {name, nickname, email, lang, twoFactor});
};
};

View File

@ -58,7 +58,7 @@ module.exports = Self => {
fields: ['name', 'twoFactor']
}, myOptions);
if (user.name !== username)
if (user.name.toLowerCase() !== username.toLowerCase())
throw new UserError('Authentication failed');
await authCode.destroy(myOptions);

View File

@ -0,0 +1,50 @@
module.exports = Self => {
Self.remoteMethodCtx('add', {
description: 'Add activity if the activity is different or is the same but have exceed time for break',
accessType: 'WRITE',
accepts: [
{
arg: 'code',
type: 'string',
description: 'Code for activity'
},
{
arg: 'model',
type: 'string',
description: 'Origin model from insert'
},
],
http: {
path: `/add`,
verb: 'POST'
}
});
Self.add = async(ctx, code, model, options) => {
const userId = ctx.req.accessToken.userId;
const myOptions = {};
if (typeof options == 'object')
Object.assign(myOptions, options);
return await Self.rawSql(`
INSERT INTO workerActivity (workerFk, workerActivityTypeFk, model)
SELECT ?, ?, ?
FROM workerTimeControlParams wtcp
LEFT JOIN (
SELECT wa.workerFk,
wa.created,
wat.code
FROM workerActivity wa
LEFT JOIN workerActivityType wat ON wat.code = wa.workerActivityTypeFk
WHERE wa.workerFk = ?
ORDER BY wa.created DESC
LIMIT 1
) sub ON TRUE
WHERE sub.workerFk IS NULL
OR sub.code <> ?
OR TIMESTAMPDIFF(SECOND, sub.created, util.VN_NOW()) > wtcp.dayBreak;`
, [userId, code, model, userId, code], myOptions);
};
};

View File

@ -0,0 +1,30 @@
const {models} = require('vn-loopback');
describe('workerActivity insert()', () => {
const ctx = beforeAll.getCtx(1106);
it('should insert in workerActivity', async() => {
const tx = await models.WorkerActivity.beginTransaction({});
let count = 0;
const options = {transaction: tx};
try {
await models.WorkerActivityType.create(
{'code': 'STOP', 'description': 'STOP'}, options
);
await models.WorkerActivity.add(ctx, 'STOP', 'APP', options);
count = await models.WorkerActivity.count(
{'workerFK': 1106}, options
);
await tx.rollback();
} catch (e) {
await tx.rollback();
throw e;
}
expect(count).toEqual(1);
});
});

View File

@ -118,6 +118,9 @@
"NotificationSubscription": {
"dataSource": "vn"
},
"OrmConfig": {
"dataSource": "vn"
},
"Province": {
"dataSource": "vn"
},

View File

@ -0,0 +1,26 @@
{
"name": "OrmConfig",
"base": "VnModel",
"options": {
"mysql": {
"table": "ormConfig"
}
},
"properties": {
"id": {
"type": "number",
"id": true
},
"selectLimit": {
"type": "number"
}
},
"acls": [
{
"accessType": "*",
"principalType": "ROLE",
"principalId": "$authenticated",
"permission": "ALLOW"
}
]
}

View File

@ -101,9 +101,10 @@ module.exports = function(Self) {
const headers = httpRequest.headers;
const origin = headers.origin;
const defaultHash = '/reset-password?access_token=$token$';
const defaultHash = '!/reset-password?access_token=$token$';
const recoverHashes = {
hedera: 'verificationToken=$token$'
hedera: '!verificationToken=$token$',
lilium: '/resetPassword?access_token=$token$'
};
const app = info.options?.app;
@ -115,7 +116,7 @@ module.exports = function(Self) {
const params = {
recipient: info.email,
lang: user.lang,
url: origin + '/#!' + recoverHash
url: origin + '/#' + recoverHash
};
const options = Object.assign({}, info.options);

View File

@ -0,0 +1,3 @@
module.exports = Self => {
require('../methods/workerActivity/add')(Self);
};

View File

@ -22,18 +22,18 @@
},
"description": {
"type": "string"
}
},
"relations": {
"workerFk": {
"type": "belongsTo",
"model": "Worker",
"foreignKey": "workerFk"
},
"relations": {
"workerFk": {
"type": "belongsTo",
"model": "Worker",
"foreignKey": "workerFk"
},
"workerActivityTypeFk": {
"type": "belongsTo",
"model": "WorkerActivityType",
"foreignKey": "workerActivityTypeFk"
}
"workerActivityTypeFk": {
"type": "belongsTo",
"model": "WorkerActivityType",
"foreignKey": "workerActivityTypeFk"
}
}
}

View File

@ -3,4 +3,5 @@ apps:
name: salix-back
instances: 1
max_restarts: 0
autorestart: false
node_args: --tls-min-v1.0 --openssl-legacy-provider

File diff suppressed because it is too large Load Diff

View File

@ -1455,6 +1455,11 @@ INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','accountingType','gu
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','bankPolicyDetail','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','bankPolicyReview','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','bankPolicy','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','edi','hedera-web','imapMultiConfig','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','hedera','salesAssistant','orderConfig','root@localhost','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','itemEntryOut','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','itemEntryIn','guillermo@db-proxy2.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
INSERT IGNORE INTO `tables_priv` VALUES ('','vn','grafana','itemShelvingSale','guillermo@db-proxy1.servers.dc.verdnatura.es','0000-00-00 00:00:00','Select','');
/*!40000 ALTER TABLE `tables_priv` ENABLE KEYS */;
/*!40000 ALTER TABLE `columns_priv` DISABLE KEYS */;
@ -2160,9 +2165,7 @@ INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','buy_recalcPricesByAwb'
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','buy_recalcPricesByEntry','PROCEDURE','jenkins@db-proxy2.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','util','hr','accountNumberToIban','FUNCTION','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','util','financial','accountNumberToIban','FUNCTION','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','administrative','supplier_statement','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','supplier_statement','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','hrBoss','supplier_statement','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','supplier_statementWithEntries','PROCEDURE','guillermo@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','adminBoss','XDiario_check','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','travel_getDetailFromContinent','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','claimManager','entry_getTransfer','PROCEDURE','jenkins@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
@ -2193,6 +2196,8 @@ INSERT IGNORE INTO `procs_priv` VALUES ('','vn','production','itemShelvingSale_
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','production','sectorCollection_getMyPartial','PROCEDURE','carlosap@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','grafana-write','item_ValuateInventory','PROCEDURE','guillermo@db-proxy1.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','guest','ticketCalculatePurge','PROCEDURE','jenkins@db-proxy2.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','buyer','buy_getUltimate','PROCEDURE','guillermo@db-proxy2.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
INSERT IGNORE INTO `procs_priv` VALUES ('','vn','cooler','buy_getUltimate','PROCEDURE','guillermo@db-proxy2.servers.dc.verdnatura.es','Execute','0000-00-00 00:00:00');
/*!40000 ALTER TABLE `procs_priv` ENABLE KEYS */;
/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
@ -2237,7 +2242,7 @@ INSERT IGNORE INTO `global_priv` VALUES ('','grafana-write','{\"access\":0,\"ve
INSERT IGNORE INTO `global_priv` VALUES ('','greenhouseBoss','{\"access\":0,\"version_id\":101106,\"is_role\":true}');
INSERT IGNORE INTO `global_priv` VALUES ('','guest','{\"access\": 0, \"max_questions\": 40000, \"max_updates\": 1000, \"max_connections\": 150000, \"max_user_connections\": 200, \"max_statement_time\": 0.000000, \"is_role\": true, \"version_id\": 101106}');
INSERT IGNORE INTO `global_priv` VALUES ('','handmadeBoss','{\"access\":0,\"version_id\":101106,\"is_role\":true}');
INSERT IGNORE INTO `global_priv` VALUES ('','hedera-web','{\"access\":0,\"version_id\":100707,\"is_role\":true}');
INSERT IGNORE INTO `global_priv` VALUES ('','hedera-web','{\"access\":0,\"version_id\":101106,\"is_role\":true}');
INSERT IGNORE INTO `global_priv` VALUES ('','hr','{\"access\": 0, \"is_role\": true, \"version_id\": 101106}');
INSERT IGNORE INTO `global_priv` VALUES ('','hrBoss','{\"access\":0,\"version_id\":101106,\"is_role\":true}');
INSERT IGNORE INTO `global_priv` VALUES ('','invoicing','{\"access\":0,\"version_id\":100707,\"is_role\":true}');

File diff suppressed because it is too large Load Diff

View File

@ -1423,6 +1423,70 @@ DELIMITER ;
--
USE `salix`;
/*!50003 SET @saved_cs_client = @@character_set_client */ ;
/*!50003 SET @saved_cs_results = @@character_set_results */ ;
/*!50003 SET @saved_col_connection = @@collation_connection */ ;
/*!50003 SET character_set_client = utf8mb4 */ ;
/*!50003 SET character_set_results = utf8mb4 */ ;
/*!50003 SET collation_connection = utf8mb4_unicode_ci */ ;
/*!50003 SET @saved_sql_mode = @@sql_mode */ ;
/*!50003 SET sql_mode = 'IGNORE_SPACE,NO_ENGINE_SUBSTITUTION' */ ;
DELIMITER ;;
/*!50003 CREATE*/ /*!50017 DEFINER=`root`@`localhost`*/ /*!50003 TRIGGER `salix`.`ACL_beforeInsert`
BEFORE INSERT ON `ACL`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END */;;
DELIMITER ;
/*!50003 SET sql_mode = @saved_sql_mode */ ;
/*!50003 SET character_set_client = @saved_cs_client */ ;
/*!50003 SET character_set_results = @saved_cs_results */ ;
/*!50003 SET collation_connection = @saved_col_connection */ ;
/*!50003 SET @saved_cs_client = @@character_set_client */ ;
/*!50003 SET @saved_cs_results = @@character_set_results */ ;
/*!50003 SET @saved_col_connection = @@collation_connection */ ;
/*!50003 SET character_set_client = utf8mb4 */ ;
/*!50003 SET character_set_results = utf8mb4 */ ;
/*!50003 SET collation_connection = utf8mb4_unicode_ci */ ;
/*!50003 SET @saved_sql_mode = @@sql_mode */ ;
/*!50003 SET sql_mode = 'IGNORE_SPACE,NO_ENGINE_SUBSTITUTION' */ ;
DELIMITER ;;
/*!50003 CREATE*/ /*!50017 DEFINER=`root`@`localhost`*/ /*!50003 TRIGGER `salix`.`ACL_beforeUpdate`
BEFORE UPDATE ON `ACL`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END */;;
DELIMITER ;
/*!50003 SET sql_mode = @saved_sql_mode */ ;
/*!50003 SET character_set_client = @saved_cs_client */ ;
/*!50003 SET character_set_results = @saved_cs_results */ ;
/*!50003 SET collation_connection = @saved_col_connection */ ;
/*!50003 SET @saved_cs_client = @@character_set_client */ ;
/*!50003 SET @saved_cs_results = @@character_set_results */ ;
/*!50003 SET @saved_col_connection = @@collation_connection */ ;
/*!50003 SET character_set_client = utf8mb4 */ ;
/*!50003 SET character_set_results = utf8mb4 */ ;
/*!50003 SET collation_connection = utf8mb4_unicode_ci */ ;
/*!50003 SET @saved_sql_mode = @@sql_mode */ ;
/*!50003 SET sql_mode = 'IGNORE_SPACE,NO_ENGINE_SUBSTITUTION' */ ;
DELIMITER ;;
/*!50003 CREATE*/ /*!50017 DEFINER=`root`@`localhost`*/ /*!50003 TRIGGER `salix`.`ACL_afterDelete`
AFTER DELETE ON `ACL`
FOR EACH ROW
BEGIN
INSERT INTO ACLLog
SET `action` = 'delete',
`changedModel` = 'Acl',
`changedModelId` = OLD.id,
`userFk` = account.myUser_getId();
END */;;
DELIMITER ;
/*!50003 SET sql_mode = @saved_sql_mode */ ;
/*!50003 SET character_set_client = @saved_cs_client */ ;
/*!50003 SET character_set_results = @saved_cs_results */ ;
/*!50003 SET collation_connection = @saved_col_connection */ ;
--
-- Current Database: `srt`
@ -9220,7 +9284,13 @@ BEGIN
SET NEW.editorFk = account.myUser_getId();
IF NOT (NEW.routeFk <=> OLD.routeFk) THEN
IF NEW.isSigned THEN
IF NEW.isSigned AND NOT (
SELECT (COUNT(s.id) = COUNT(cb.saleFk)
AND SUM(s.quantity) = SUM(cb.quantity))
FROM sale s
LEFT JOIN claimBeginning cb ON cb.saleFk = s.id
WHERE s.ticketFk = NEW.id
) THEN
CALL util.throw('A signed ticket cannot be rerouted');
END IF;
INSERT IGNORE INTO routeRecalc(routeFk)
@ -11142,4 +11212,4 @@ USE `vn2008`;
/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;
-- Dump completed on 2024-08-06 6:03:19
-- Dump completed on 2024-08-20 7:45:23

View File

@ -412,7 +412,7 @@ INSERT INTO `vn`.`clientManaCache`(`clientFk`, `mana`, `dated`)
(1103, 0, DATE_ADD(util.VN_CURDATE(), INTERVAL -1 MONTH)),
(1104, -30, DATE_ADD(util.VN_CURDATE(), INTERVAL -1 MONTH));
INSERT INTO `vn`.`mandateType`(`id`, `name`)
INSERT INTO `vn`.`mandateType`(`id`, `code`)
VALUES
(1, 'B2B'),
(2, 'CORE'),
@ -632,7 +632,7 @@ INSERT INTO `vn`.`invoiceOutSerial` (`code`, `description`, `isTaxed`, `taxAreaF
('A', 'Global nacional', 1, 'NATIONAL', 0, 'global'),
('T', 'Española rapida', 1, 'NATIONAL', 0, 'quick'),
('V', 'Intracomunitaria global', 0, 'CEE', 1, 'global'),
('M', 'Múltiple nacional', 1, 'NATIONAL', 0, 'quick'),
('M', 'Múltiple nacional', 1, 'NATIONAL', 0, 'multiple'),
('R', 'Rectificativa', 1, 'NATIONAL', 0, NULL),
('E', 'Exportación rápida', 0, 'WORLD', 0, 'quick');
@ -1516,7 +1516,7 @@ INSERT INTO `vn`.`entry`(`id`, `supplierFk`, `created`, `travelFk`, `isConfirmed
(9, 2, DATE_ADD(util.VN_CURDATE(), INTERVAL +2 DAY), 10, 0, 442, 'IN2009', 'Movement 9', 1, 1, ''),
(10, 2, DATE_ADD(util.VN_CURDATE(), INTERVAL +2 DAY), 10, 0, 442, 'IN2009', 'Movement 9', 1, 1, '');
INSERT INTO `bs`.`waste`(`buyerFk`, `year`, `week`, `itemFk`, `itemTypeFk`, `saleTotal`, `saleQuantity`, `saleInternalWaste`, `saleExternalWaste`)
INSERT INTO `bs`.`waste`(`buyerFk`, `year`, `week`, `itemFk`, `itemTypeFk`, `saleTotal`, `saleWasteQuantity`, `saleInternalWaste`, `saleExternalWaste`)
VALUES
('35', YEAR(DATE_ADD(util.VN_CURDATE(), INTERVAL -1 WEEK)), WEEK(DATE_ADD(util.VN_CURDATE(), INTERVAL -1 WEEK), 1), 1, 1, '1062', '51', '56.20', '56.20'),
('35', YEAR(DATE_ADD(util.VN_CURDATE(), INTERVAL -1 WEEK)), WEEK(DATE_ADD(util.VN_CURDATE(), INTERVAL -1 WEEK), 1), 2, 1, '35074', '687', '53.12', '89.69'),
@ -3945,11 +3945,11 @@ VALUES
(35, 'ES12346B12345679', 3, 241);
INSERT INTO vn.accountDetailType
(id, description)
(id, description, code)
VALUES
(1, 'IBAN'),
(2, 'SWIFT'),
(3, 'Referencia Remesas'),
(4, 'Referencia Transferencias'),
(5, 'Referencia Nominas'),
(6, 'ABA');
(1, 'IBAN', 'iban'),
(2, 'SWIFT', 'swift'),
(3, 'Referencia Remesas', 'remRef'),
(4, 'Referencia Transferencias', 'trnRef'),
(5, 'Referencia Nominas', 'payRef'),
(6, 'ABA', 'aba');

View File

@ -1,7 +1,7 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `bs`.`waste_addSales`()
BEGIN
DECLARE vDateFrom DATE DEFAULT util.VN_CURDATE() - INTERVAL WEEKDAY(CURDATE()) DAY;
DECLARE vDateFrom DATE DEFAULT util.VN_CURDATE() - INTERVAL WEEKDAY(util.VN_CURDATE()) DAY;
DECLARE vDateTo DATE DEFAULT vDateFrom + INTERVAL 6 DAY;
CALL cache.last_buy_refresh(FALSE);
@ -12,25 +12,22 @@ BEGIN
it.workerFk,
it.id,
s.itemFk,
SUM(s.quantity),
SUM((b.buyingValue + b.freightValue + b.comissionValue + b.packageValue) * s.quantity) `value`,
SUM (
SUM((b.buyingValue + b.freightValue + b.comissionValue + b.packageValue) * s.quantity),
SUM(IF(aw.`type`, s.quantity, 0)),
SUM(
IF(
aw.`type` = 'internal',
(b.buyingValue + b.freightValue + b.comissionValue + b.packageValue) * s.quantity,
0
)
) internalWaste,
SUM (
),
SUM(
IF(
aw.`type` = 'external',
(b.buyingValue + b.freightValue + b.comissionValue + b.packageValue) * s.quantity,
IF(c.code = 'manaClaim',
sc.value * s.quantity,
0
)
0
)
) externalWaste
)
FROM vn.sale s
JOIN vn.item i ON i.id = s.itemFk
JOIN vn.itemType it ON it.id = i.typeFk
@ -41,10 +38,8 @@ BEGIN
JOIN cache.last_buy lb ON lb.item_id = i.id
AND lb.warehouse_id = w.id
JOIN vn.buy b ON b.id = lb.buy_id
LEFT JOIN vn.saleComponent sc ON sc.saleFk = s.id
LEFT JOIN vn.component c ON c.id = sc.componentFk
WHERE t.shipped BETWEEN vDateFrom AND vDateTo
AND w.isManaged
GROUP BY it.id, i.id;
GROUP BY i.id;
END$$
DELIMITER ;

View File

@ -3,7 +3,7 @@ CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `salix`.`ACL_afterDelete`
AFTER DELETE ON `ACL`
FOR EACH ROW
BEGIN
INSERT INTO ACL
INSERT INTO ACLLog
SET `action` = 'delete',
`changedModel` = 'Acl',
`changedModelId` = OLD.id,

View File

@ -1,13 +1,9 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` EVENT `srt`.`moving_clean`
ON SCHEDULE EVERY 5 MINUTE
ON SCHEDULE EVERY 15 MINUTE
STARTS '2022-01-21 00:00:00.000'
ON COMPLETION PRESERVE
ENABLE
COMMENT 'Llama a srt.moving_clean para que elimine y notifique de registr'
DO BEGIN
CALL srt.moving_clean();
END$$
DO CALL srt.moving_clean()$$
DELIMITER ;

View File

@ -3,61 +3,69 @@ CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `srt`.`moving_clean`()
BEGIN
/**
* Elimina movimientos por inactividad
*
*/
DECLARE vExpeditionFk INT;
DECLARE vBufferToFk INT;
DECLARE vBufferFromFk INT;
DECLARE done BOOL DEFAULT FALSE;
DECLARE cur CURSOR FOR
SELECT m.expeditionFk, m.bufferToFk, m.bufferFromFk
FROM srt.moving m
JOIN srt.config c
JOIN (SELECT bufferFk, SUM(isActive) hasBox
FROM srt.photocell
GROUP BY bufferFk) sub ON sub.bufferFk = m.bufferFromFk
WHERE m.created < TIMESTAMPADD(MINUTE, - c.movingMaxLife , util.VN_NOW())
DECLARE vStateOutFk INT
DEFAULT (SELECT id FROM expeditionState WHERE `description` = 'OUT');
DECLARE vDone BOOL;
DECLARE vSorter CURSOR FOR
SELECT m.expeditionFk, m.bufferFromFk
FROM moving m
JOIN (
SELECT bufferFk, SUM(isActive) hasBox
FROM photocell
GROUP BY bufferFk
) sub ON sub.bufferFk = m.bufferFromFk
WHERE m.created < (util.VN_NOW() - INTERVAL (SELECT movingMaxLife FROM config) MINUTE)
AND NOT sub.hasBox;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = 1;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET vDone = TRUE;
OPEN cur;
DECLARE EXIT HANDLER FOR SQLEXCEPTION
BEGIN
ROLLBACK;
RESIGNAL;
END;
bucle: LOOP
OPEN vSorter;
l: LOOP
SET vDone = FALSE;
FETCH vSorter INTO vExpeditionFk, vBufferFromFk;
FETCH cur INTO vExpeditionFk, vBufferToFk, vBufferFromFk;
IF done THEN
LEAVE bucle;
IF vDone THEN
LEAVE l;
END IF;
DELETE FROM srt.moving
START TRANSACTION;
SELECT id
FROM moving
WHERE expeditionFk = vExpeditionFk
FOR UPDATE;
DELETE FROM moving
WHERE expeditionFk = vExpeditionFk;
UPDATE srt.expedition e
JOIN srt.expeditionState es ON es.description = 'OUT'
SET
bufferFk = NULL,
SELECT id
FROM expedition
WHERE id = vExpeditionFk
OR (bufferFk = vBufferFromFk AND `position` > 0)
FOR UPDATE;
UPDATE expedition
SET bufferFk = NULL,
`position` = NULL,
stateFk = es.id
WHERE e.id = vExpeditionFk;
stateFk = vStateOutFk
WHERE id = vExpeditionFk;
UPDATE srt.expedition e
SET e.`position` = e.`position` - 1
WHERE e.bufferFk = vBufferFromFk
AND e.`position` > 0;
CALL vn.mail_insert(
'pako@verdnatura.es, carles@verdnatura.es',
NULL,
CONCAT('Moving_clean. Expedition: ', vExpeditionFk, ' estaba parada'),
CONCAT('Expedition: ', vExpeditionFk,' vBufferToFk: ', vBufferToFk)
);
END LOOP bucle;
CLOSE cur;
UPDATE expedition
SET `position` = `position` - 1
WHERE bufferFk = vBufferFromFk
AND `position` > 0;
COMMIT;
END LOOP l;
CLOSE vSorter;
END$$
DELIMITER ;

View File

@ -0,0 +1,12 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`buffer_afterDelete`
AFTER DELETE ON `buffer`
FOR EACH ROW
BEGIN
INSERT INTO buffer
SET `action` = 'delete',
`changedModel` = 'Buffer',
`changedModelId` = OLD.id,
`userFk` = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`buffer_beforeInsert`
BEFORE INSERT ON `buffer`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`buffer_beforeUpdate`
BEFORE UPDATE ON `buffer`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,12 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`config_afterDelete`
AFTER DELETE ON `config`
FOR EACH ROW
BEGIN
INSERT INTO config
SET `action` = 'delete',
`changedModel` = 'Config',
`changedModelId` = OLD.id,
`userFk` = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`config_beforeInsert`
BEFORE INSERT ON `config`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `srt`.`config_beforeUpdate`
BEFORE UPDATE ON `config`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -1,26 +1,32 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` FUNCTION `vn`.`invoiceSerial`(vClientFk INT, vCompanyFk INT, vType CHAR(1))
RETURNS char(1) CHARSET utf8mb3 COLLATE utf8mb3_general_ci
CREATE OR REPLACE DEFINER=`root`@`localhost` FUNCTION `vn`.`invoiceSerial`(vClientFk INT, vCompanyFk INT, vType CHAR(15))
RETURNS char(2) CHARSET utf8mb3 COLLATE utf8mb3_general_ci
DETERMINISTIC
BEGIN
/**
* Obtiene la serie de de una factura
* Obtiene la serie de una factura
* dependiendo del area del cliente.
*
*
* @param vClientFk Id del cliente
* @param vCompanyFk Id de la empresa
* @param vType Tipo de factura ["R", "M", "G"]
* @return Serie de la factura
* @param vType Tipo de factura ['global','multiple','quick']
* @return vSerie de la factura
*/
DECLARE vTaxArea VARCHAR(25);
DECLARE vSerie CHAR(1);
DECLARE vTaxArea VARCHAR(25) COLLATE utf8mb3_general_ci;
DECLARE vSerie CHAR(2);
IF (SELECT hasInvoiceSimplified FROM client WHERE id = vClientFk) THEN
RETURN 'S';
END IF;
SELECT clientTaxArea(vClientFk, vCompanyFk) INTO vTaxArea;
SELECT invoiceSerialArea(vType,vTaxArea) INTO vSerie;
SELECT addressTaxArea(defaultAddressFk, vCompanyFk) INTO vTaxArea
FROM client
WHERE id = vClientFk;
SELECT code INTO vSerie
FROM invoiceOutSerial
WHERE `type` = vType AND taxAreaFk = vTaxArea;
RETURN vSerie;
END$$
DELIMITER ;

View File

@ -1,34 +0,0 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` FUNCTION `vn`.`invoiceSerialArea`(vType CHAR(1), vTaxArea VARCHAR(25))
RETURNS char(1) CHARSET utf8mb3 COLLATE utf8mb3_unicode_ci
DETERMINISTIC
BEGIN
DECLARE vSerie CHAR(1);
IF vType = 'R' THEN
SELECT
CASE vTaxArea
WHEN 'CEE' THEN 'H'
WHEN 'WORLD' THEN 'E'
ELSE 'T'
END INTO vSerie;
-- Factura multiple
ELSEIF vType = 'M' THEN
SELECT
CASE vTaxArea
WHEN 'CEE' THEN 'H'
WHEN 'WORLD' THEN 'E'
ELSE 'M'
END INTO vSerie;
-- Factura global
ELSEIF vType = 'G' THEN
SELECT
CASE vTaxArea
WHEN 'CEE' THEN 'V'
WHEN 'WORLD' THEN 'X'
ELSE 'A'
END INTO vSerie;
END IF;
RETURN vSerie;
END$$
DELIMITER ;

View File

@ -1,8 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `vn`.`address_updateCoordinates`(
vTicketFk INT,
vLongitude INT,
vLatitude INT)
vLongitude DECIMAL(11,7),
vLatitude DECIMAL(11,7))
BEGIN
/**
* Actualiza las coordenadas de una dirección.

View File

@ -21,6 +21,7 @@ BEGIN
AND a.id IS NULL
AND u.active
AND c.created < util.VN_CURDATE() - INTERVAL vMonths MONTH
AND NOT u.role = (SELECT id FROM `role` WHERE name = 'supplier')
AND u.id NOT IN (
SELECT DISTINCT c.id
FROM client c

View File

@ -9,10 +9,11 @@ BEGIN
DECLARE vWarehouseFk INT;
DECLARE vWagons INT;
DECLARE vTrainFk INT;
DECLARE vLinesLimit INT DEFAULT NULL;
DECLARE vLinesLimit INT;
DECLARE vTicketLines INT;
DECLARE vVolumeLimit DECIMAL DEFAULT NULL;
DECLARE vVolumeLimit DECIMAL;
DECLARE vTicketVolume DECIMAL;
DECLARE vSizeLimit INT;
DECLARE vMaxTickets INT;
DECLARE vStateFk VARCHAR(45);
DECLARE vFirstTicketFk INT;
@ -77,6 +78,7 @@ BEGIN
o.trainFk,
o.linesLimit,
o.volumeLimit,
o.sizeLimit,
pc.collection_new_lockname
INTO vMaxTickets,
vHasUniqueCollectionTime,
@ -88,6 +90,7 @@ BEGIN
vTrainFk,
vLinesLimit,
vVolumeLimit,
vSizeLimit,
vLockName
FROM productionConfig pc
JOIN worker w ON w.id = vUserFk
@ -172,6 +175,14 @@ BEGIN
JOIN state s ON s.id = pb.state
JOIN agencyMode am ON am.id = pb.agencyModeFk
JOIN agency a ON a.id = am.agencyFk
LEFT JOIN (
SELECT pb.ticketFk, MAX(i.`size`) maxSize
FROM tmp.productionBuffer pb
JOIN ticket t ON t.id = pb.ticketfk
JOIN sale s ON s.ticketFk = t.id
JOIN item i ON i.id = s.itemFk
GROUP BY pb.ticketFk
) sub ON sub.ticketFk = pb.ticketFk
JOIN productionConfig pc
WHERE pb.shipped <> util.VN_CURDATE()
OR (pb.ubicacion IS NULL AND a.isOwn)
@ -183,8 +194,9 @@ BEGIN
OR (NOT pb.V AND vItemPackingTypeFk = 'V')
OR (pc.isPreviousPreparationRequired AND pb.previousWithoutParking)
OR LENGTH(pb.problem) > 0
OR (pb.lines >= vLinesLimit AND vLinesLimit IS NOT NULL)
OR (pb.m3 >= vVolumeLimit AND vVolumeLimit IS NOT NULL);
OR (pb.lines > vLinesLimit AND vLinesLimit IS NOT NULL)
OR (pb.m3 > vVolumeLimit AND vVolumeLimit IS NOT NULL)
OR ((sub.maxSize > vSizeLimit OR sub.maxSize IS NOT NULL) AND vSizeLimit IS NOT NULL);
END IF;
-- Es importante que el primer ticket se coja en todos los casos

View File

@ -15,7 +15,7 @@ BEGIN
DECLARE cur CURSOR FOR
SELECT bb.id buyFk,
FLOOR(ish.visible / ish.packing) ishStickers,
LEAST(bb.stickers, FLOOR(ish.visible / ish.packing)) ishStickers,
bb.stickers buyStickers
FROM itemShelving ish
JOIN (SELECT b.id, b.itemFk, b.stickers
@ -23,7 +23,6 @@ BEGIN
WHERE b.entryFk = vFromEntryFk
ORDER BY b.stickers DESC
LIMIT 10000000000000000000) bb ON bb.itemFk = ish.itemFk
AND bb.stickers >= FLOOR(ish.visible / ish.packing)
WHERE ish.shelvingFk = vShelvingFk COLLATE utf8_general_ci
AND NOT ish.isSplit
GROUP BY ish.id;

View File

@ -97,7 +97,7 @@ BEGIN
AND (vCorrectingSerial = vSerial OR NOT hasAnyNegativeBase())
THEN
-- el trigger añade el siguiente Id_Factura correspondiente a la vSerial
-- el trigger añade el siguiente ref correspondiente a la vSerial
INSERT INTO invoiceOut(
ref,
serial,

View File

@ -12,7 +12,7 @@ BEGIN
DECLARE vSaleFk INT;
DECLARE vSectorFk INT;
DECLARE vSales CURSOR FOR
SELECT s.id
SELECT DISTINCT s.id
FROM sectorCollectionSaleGroup sc
JOIN saleGroupDetail sg ON sg.saleGroupFk = sc.saleGroupFk
JOIN sale s ON sg.saleFk = s.id

View File

@ -1,139 +0,0 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `vn`.`supplier_statement`(
vSupplierFk INT,
vCurrencyFk INT,
vCompanyFk INT,
vOrderBy VARCHAR(15),
vIsConciliated BOOL
)
BEGIN
/**
* Crea un estado de cuenta de proveedores calculando
* los saldos en euros y en la moneda especificada.
*
* @param vSupplierFk Id del proveedor
* @param vCurrencyFk Id de la moneda
* @param vCompanyFk Id de la empresa
* @param vOrderBy Criterio de ordenación
* @param vIsConciliated Indica si está conciliado o no
* @return tmp.supplierStatement
*/
SET @euroBalance:= 0;
SET @currencyBalance:= 0;
CREATE OR REPLACE TEMPORARY TABLE tmp.supplierStatement
ENGINE = MEMORY
SELECT *,
@euroBalance:= ROUND(
@euroBalance + IFNULL(paymentEuros, 0) -
IFNULL(invoiceEuros, 0), 2
) euroBalance,
@currencyBalance:= ROUND(
@currencyBalance + IFNULL(paymentCurrency, 0) -
IFNULL(invoiceCurrency, 0), 2
) currencyBalance
FROM (
SELECT * FROM
(
SELECT NULL bankFk,
ii.companyFk,
ii.serial,
ii.id,
CASE
WHEN vOrderBy = 'issued' THEN ii.issued
WHEN vOrderBy = 'bookEntried' THEN ii.bookEntried
WHEN vOrderBy = 'booked' THEN ii.booked
WHEN vOrderBy = 'dueDate' THEN iid.dueDated
END dated,
CONCAT('S/Fra ', ii.supplierRef) sref,
IF(ii.currencyFk > 1,
ROUND(SUM(iid.foreignValue) / SUM(iid.amount), 3),
NULL
) changeValue,
CAST(SUM(iid.amount) AS DECIMAL(10,2)) invoiceEuros,
CAST(SUM(iid.foreignValue) AS DECIMAL(10,2)) invoiceCurrency,
NULL paymentEuros,
NULL paymentCurrency,
ii.currencyFk,
ii.isBooked,
c.code,
'invoiceIn' statementType
FROM invoiceIn ii
JOIN invoiceInDueDay iid ON iid.invoiceInFk = ii.id
JOIN currency c ON c.id = ii.currencyFk
WHERE ii.issued > '2014-12-31'
AND ii.supplierFk = vSupplierFk
AND vCurrencyFk IN (ii.currencyFk, 0)
AND vCompanyFk IN (ii.companyFk, 0)
AND (vIsConciliated = ii.isBooked OR NOT vIsConciliated)
GROUP BY iid.id
UNION ALL
SELECT p.bankFk,
p.companyFk,
NULL,
p.id,
CASE
WHEN vOrderBy = 'issued' THEN p.received
WHEN vOrderBy = 'bookEntried' THEN p.received
WHEN vOrderBy = 'booked' THEN p.received
WHEN vOrderBy = 'dueDate' THEN p.dueDated
END,
CONCAT(IFNULL(pm.name, ''),
IF(pn.concept <> '',
CONCAT(' : ', pn.concept),
'')
),
IF(p.currencyFk > 1, p.divisa / p.amount, NULL),
NULL,
NULL,
p.amount,
p.divisa,
p.currencyFk,
p.isConciliated,
c.code,
'payment'
FROM payment p
LEFT JOIN currency c ON c.id = p.currencyFk
LEFT JOIN accounting a ON a.id = p.bankFk
LEFT JOIN payMethod pm ON pm.id = p.payMethodFk
LEFT JOIN promissoryNote pn ON pn.paymentFk = p.id
WHERE p.received > '2014-12-31'
AND p.supplierFk = vSupplierFk
AND vCurrencyFk IN (p.currencyFk, 0)
AND vCompanyFk IN (p.companyFk, 0)
AND (vIsConciliated = p.isConciliated OR NOT vIsConciliated)
UNION ALL
SELECT NULL,
companyFk,
NULL,
se.id,
CASE
WHEN vOrderBy = 'issued' THEN se.dated
WHEN vOrderBy = 'bookEntried' THEN se.dated
WHEN vOrderBy = 'booked' THEN se.dated
WHEN vOrderBy = 'dueDate' THEN se.dueDated
END,
se.description,
1,
amount,
NULL,
NULL,
NULL,
currencyFk,
isConciliated,
c.`code`,
'expense'
FROM supplierExpense se
JOIN currency c ON c.id = se.currencyFk
WHERE se.supplierFk = vSupplierFk
AND vCurrencyFk IN (se.currencyFk,0)
AND vCompanyFk IN (se.companyFk,0)
AND (vIsConciliated = se.isConciliated OR NOT vIsConciliated)
) sub
ORDER BY (dated IS NULL AND NOT isBooked),
dated,
IF(vOrderBy = 'dueDate', id, NULL)
LIMIT 10000000000000000000
) t;
END$$
DELIMITER ;

View File

@ -0,0 +1,166 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE vn.supplier_statementWithEntries(
vSupplierFk INT,
vCurrencyFk INT,
vCompanyFk INT,
vOrderBy VARCHAR(15),
vIsConciliated BOOL,
vHasEntries BOOL
)
BEGIN
/**
* Creates a supplier statement, calculating balances in euros and the specified currency.
*
* @param vSupplierFk Supplier ID
* @param vCurrencyFk Currency ID
* @param vCompanyFk Company ID
* @param vOrderBy Order by criteria
* @param vIsConciliated Indicates whether it is reconciled or not
* @param vHasEntries Indicates if future entries must be shown
* @return tmp.supplierStatement
*/
DECLARE vBalanceStartingDate DATETIME;
SET @euroBalance:= 0;
SET @currencyBalance:= 0;
SELECT balanceStartingDate
INTO vBalanceStartingDate
FROM invoiceInConfig;
CREATE OR REPLACE TEMPORARY TABLE tmp.supplierStatement
ENGINE = MEMORY
SELECT *,
@euroBalance:= ROUND(
@euroBalance + IFNULL(paymentEuros, 0) -
IFNULL(invoiceEuros, 0), 2
) euroBalance,
@currencyBalance:= ROUND(
@currencyBalance + IFNULL(paymentCurrency, 0) -
IFNULL(invoiceCurrency, 0), 2
) currencyBalance
FROM (
SELECT NULL bankFk,
ii.companyFk,
ii.serial,
ii.id,
CASE
WHEN vOrderBy = 'issued' THEN ii.issued
WHEN vOrderBy = 'bookEntried' THEN ii.bookEntried
WHEN vOrderBy = 'booked' THEN ii.booked
WHEN vOrderBy = 'dueDate' THEN iid.dueDated
END dated,
CONCAT('S/Fra ', ii.supplierRef) sref,
IF(ii.currencyFk > 1,
ROUND(SUM(iid.foreignValue) / SUM(iid.amount), 3),
NULL
) changeValue,
CAST(SUM(iid.amount) AS DECIMAL(10,2)) invoiceEuros,
CAST(SUM(iid.foreignValue) AS DECIMAL(10,2)) invoiceCurrency,
NULL paymentEuros,
NULL paymentCurrency,
ii.currencyFk,
ii.isBooked,
c.code,
'invoiceIn' statementType
FROM invoiceIn ii
JOIN invoiceInDueDay iid ON iid.invoiceInFk = ii.id
JOIN currency c ON c.id = ii.currencyFk
WHERE ii.issued >= vBalanceStartingDate
AND ii.supplierFk = vSupplierFk
AND vCurrencyFk IN (ii.currencyFk, 0)
AND vCompanyFk IN (ii.companyFk, 0)
AND (vIsConciliated = ii.isBooked OR NOT vIsConciliated)
GROUP BY iid.id
UNION ALL
SELECT p.bankFk,
p.companyFk,
NULL,
p.id,
CASE
WHEN vOrderBy = 'issued' THEN p.received
WHEN vOrderBy = 'bookEntried' THEN p.received
WHEN vOrderBy = 'booked' THEN p.received
WHEN vOrderBy = 'dueDate' THEN p.dueDated
END,
CONCAT(IFNULL(pm.name, ''),
IF(pn.concept <> '',
CONCAT(' : ', pn.concept),
'')
),
IF(p.currencyFk > 1, p.divisa / p.amount, NULL),
NULL,
NULL,
p.amount,
p.divisa,
p.currencyFk,
p.isConciliated,
c.code,
'payment'
FROM payment p
LEFT JOIN currency c ON c.id = p.currencyFk
LEFT JOIN accounting a ON a.id = p.bankFk
LEFT JOIN payMethod pm ON pm.id = p.payMethodFk
LEFT JOIN promissoryNote pn ON pn.paymentFk = p.id
WHERE p.received >= vBalanceStartingDate
AND p.supplierFk = vSupplierFk
AND vCurrencyFk IN (p.currencyFk, 0)
AND vCompanyFk IN (p.companyFk, 0)
AND (vIsConciliated = p.isConciliated OR NOT vIsConciliated)
UNION ALL
SELECT NULL,
companyFk,
NULL,
se.id,
CASE
WHEN vOrderBy = 'issued' THEN se.dated
WHEN vOrderBy = 'bookEntried' THEN se.dated
WHEN vOrderBy = 'booked' THEN se.dated
WHEN vOrderBy = 'dueDate' THEN se.dueDated
END,
se.description,
1,
amount,
NULL,
NULL,
NULL,
currencyFk,
isConciliated,
c.`code`,
'expense'
FROM supplierExpense se
JOIN currency c ON c.id = se.currencyFk
WHERE se.supplierFk = vSupplierFk
AND vCurrencyFk IN (se.currencyFk,0)
AND vCompanyFk IN (se.companyFk,0)
AND (vIsConciliated = se.isConciliated OR NOT vIsConciliated)
UNION ALL
SELECT NULL bankFk,
e.companyFk,
'E' serial,
e.invoiceNumber id,
tr.landed dated,
CONCAT('Ent. ',e.id) sref,
1 / ((e.commission/100)+1) changeValue,
e.invoiceAmount * (1 + (e.commission/100)),
e.invoiceAmount,
NULL,
NULL,
e.currencyFk,
FALSE isBooked,
c.code,
'order'
FROM entry e
JOIN travel tr ON tr.id = e.travelFk
JOIN currency c ON c.id = e.currencyFk
WHERE e.supplierFk = vSupplierFk
AND tr.landed >= CURDATE()
AND e.invoiceInFk IS NULL
AND vHasEntries
ORDER BY (dated IS NULL AND NOT isBooked),
dated,
IF(vOrderBy = 'dueDate', id, NULL)
LIMIT 10000000000000000000
) t;
END$$
DELIMITER ;

View File

@ -4,7 +4,6 @@ CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `vn`.`ticket_cloneWeekly`
vDateTo DATE
)
BEGIN
DECLARE vIsDone BOOL;
DECLARE vLanding DATE;
DECLARE vShipment DATE;
DECLARE vWarehouseFk INT;
@ -15,36 +14,37 @@ BEGIN
DECLARE vAgencyModeFk INT;
DECLARE vNewTicket INT;
DECLARE vYear INT;
DECLARE vSalesPersonFK INT;
DECLARE vItemPicker INT;
DECLARE vObservationSalesPersonFk INT
DEFAULT (SELECT id FROM observationType WHERE code = 'salesPerson');
DECLARE vObservationItemPickerFk INT
DEFAULT (SELECT id FROM observationType WHERE code = 'itemPicker');
DECLARE vEmail VARCHAR(255);
DECLARE vIsDuplicateMail BOOL;
DECLARE vSubject VARCHAR(100);
DECLARE vMessage TEXT;
DECLARE vDone BOOL;
DECLARE rsTicket CURSOR FOR
SELECT tt.ticketFk,
t.clientFk,
t.warehouseFk,
t.companyFk,
t.addressFk,
tt.agencyModeFk,
ti.dated
FROM ticketWeekly tt
JOIN ticket t ON tt.ticketFk = t.id
JOIN tmp.time ti
WHERE WEEKDAY(ti.dated) = tt.weekDay;
DECLARE vTickets CURSOR FOR
SELECT tt.ticketFk,
t.clientFk,
t.warehouseFk,
t.companyFk,
t.addressFk,
tt.agencyModeFk,
ti.dated
FROM ticketWeekly tt
JOIN ticket t ON tt.ticketFk = t.id
JOIN tmp.time ti
WHERE WEEKDAY(ti.dated) = tt.weekDay;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET vIsDone = TRUE;
CALL `util`.`time_generate`(vDateFrom,vDateTo);
OPEN rsTicket;
myLoop: LOOP
BEGIN
DECLARE vSalesPersonEmail VARCHAR(150);
DECLARE vIsDuplicateMail BOOL;
DECLARE vSubject VARCHAR(150);
DECLARE vMessage TEXT;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET vDone = TRUE;
SET vIsDone = FALSE;
FETCH rsTicket INTO
CALL `util`.`time_generate`(vDateFrom, vDateTo);
OPEN vTickets;
l: LOOP
SET vDone = FALSE;
FETCH vTickets INTO
vTicketFk,
vClientFk,
vWarehouseFk,
@ -53,11 +53,11 @@ BEGIN
vAgencyModeFk,
vShipment;
IF vIsDone THEN
LEAVE myLoop;
IF vDone THEN
LEAVE l;
END IF;
-- busca si el ticket ya ha sido clonado
-- Busca si el ticket ya ha sido clonado
IF EXISTS (SELECT TRUE FROM ticket tOrig
JOIN sale saleOrig ON tOrig.id = saleOrig.ticketFk
JOIN saleCloned sc ON sc.saleOriginalFk = saleOrig.id
@ -67,7 +67,7 @@ BEGIN
AND tClon.isDeleted = FALSE
AND DATE(tClon.shipped) = vShipment)
THEN
ITERATE myLoop;
ITERATE l;
END IF;
IF vAgencyModeFk IS NULL THEN
@ -107,15 +107,15 @@ BEGIN
priceFixed,
isPriceFixed)
SELECT vNewTicket,
saleOrig.itemFk,
saleOrig.concept,
saleOrig.quantity,
saleOrig.price,
saleOrig.discount,
saleOrig.priceFixed,
saleOrig.isPriceFixed
FROM sale saleOrig
WHERE saleOrig.ticketFk = vTicketFk;
itemFk,
concept,
quantity,
price,
discount,
priceFixed,
isPriceFixed
FROM sale
WHERE ticketFk = vTicketFk;
INSERT IGNORE INTO saleCloned(saleOriginalFk, saleClonedFk)
SELECT saleOriginal.id, saleClon.id
@ -152,15 +152,7 @@ BEGIN
attenderFk,
vNewTicket
FROM ticketRequest
WHERE ticketFk =vTicketFk;
SELECT id INTO vSalesPersonFK
FROM observationType
WHERE code = 'salesPerson';
SELECT id INTO vItemPicker
FROM observationType
WHERE code = 'itemPicker';
WHERE ticketFk = vTicketFk;
INSERT INTO ticketObservation(
ticketFk,
@ -168,7 +160,7 @@ BEGIN
description)
VALUES(
vNewTicket,
vSalesPersonFK,
vObservationSalesPersonFk,
CONCAT('turno desde ticket: ',vTicketFk))
ON DUPLICATE KEY UPDATE description =
CONCAT(ticketObservation.description,VALUES(description),' ');
@ -178,16 +170,17 @@ BEGIN
description)
VALUES(
vNewTicket,
vItemPicker,
vObservationItemPickerFk,
'ATENCION: Contiene lineas de TURNO')
ON DUPLICATE KEY UPDATE description =
CONCAT(ticketObservation.description,VALUES(description),' ');
IF (vLanding IS NULL) THEN
SELECT e.email INTO vSalesPersonEmail
IF vLanding IS NULL THEN
SELECT IFNULL(d.notificationEmail, e.email) INTO vEmail
FROM client c
JOIN account.emailUser e ON e.userFk = c.salesPersonFk
LEFT JOIN workerDepartment wd ON wd.workerFk = c.salesPersonFk
LEFT JOIN department d ON d.id = wd.departmentFk
WHERE c.id = vClientFk;
SET vSubject = CONCAT('Turnos - No se ha podido clonar correctamente el ticket ',
@ -199,20 +192,21 @@ BEGIN
SELECT COUNT(*) INTO vIsDuplicateMail
FROM mail
WHERE receiver = vSalesPersonEmail
WHERE receiver = vEmail
AND subject = vSubject;
IF NOT vIsDuplicateMail THEN
CALL mail_insert(vSalesPersonEmail, NULL, vSubject, vMessage);
CALL mail_insert(vEmail, NULL, vSubject, vMessage);
END IF;
CALL ticket_setState(vNewTicket, 'FIXING');
ELSE
CALL ticketCalculateClon(vNewTicket, vTicketFk);
END IF;
END;
END LOOP;
CLOSE rsTicket;
DROP TEMPORARY TABLE IF EXISTS tmp.time, tmp.zoneGetLanded;
CLOSE vTickets;
DROP TEMPORARY TABLE IF EXISTS
tmp.time,
tmp.zoneGetLanded;
END$$
DELIMITER ;

View File

@ -2,7 +2,7 @@ DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` PROCEDURE `vn`.`ticket_close`()
BEGIN
/**
* Realiza el cierre de todos los
* Realiza el cierre de todos los
* tickets de la tabla tmp.ticket_close.
*
* @table tmp.ticket_close(ticketFk) Identificadores de los tickets a cerrar
@ -20,7 +20,7 @@ BEGIN
DECLARE cur CURSOR FOR
SELECT ticketFk FROM tmp.ticket_close;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET vDone = TRUE;
DECLARE EXIT HANDLER FOR SQLEXCEPTION BEGIN
RESIGNAL;
@ -30,7 +30,7 @@ BEGIN
proc: LOOP
SET vDone = FALSE;
FETCH cur INTO vCurTicketFk;
IF vDone THEN
@ -47,12 +47,12 @@ BEGIN
c.hasToInvoice
INTO vClientFk,
vIsTaxDataChecked,
vCompanyFk,
vCompanyFk,
vShipped,
vHasDailyInvoice,
vWithPackage,
vHasToInvoice
FROM ticket t
FROM ticket t
JOIN `client` c ON c.id = t.clientFk
JOIN province p ON p.id = c.provinceFk
LEFT JOIN autonomy a ON a.id = p.autonomyFk
@ -62,7 +62,7 @@ BEGIN
INSERT INTO ticketPackaging (ticketFk, packagingFk, quantity)
(SELECT vCurTicketFk, p.id, COUNT(*)
FROM expedition e
FROM expedition e
JOIN packaging p ON p.id = e.packagingFk
JOIN ticket t ON t.id = e.ticketFk
LEFT JOIN agencyMode am ON am.id = t.agencyModeFk
@ -73,15 +73,15 @@ BEGIN
GROUP BY p.itemFk);
-- No retornables o no catalogados
INSERT INTO sale (itemFk, ticketFk, concept, quantity, price, isPriceFixed)
INSERT INTO sale (itemFk, ticketFk, concept, quantity, price, isPriceFixed)
(SELECT e.freightItemFk, vCurTicketFk, i.name, COUNT(*) AS amount, getSpecialPrice(e.freightItemFk, vClientFk), 1
FROM expedition e
FROM expedition e
JOIN item i ON i.id = e.freightItemFk
LEFT JOIN packaging p ON p.itemFk = i.id
WHERE e.ticketFk = vCurTicketFk AND IFNULL(p.isPackageReturnable, 0) = 0
AND getSpecialPrice(e.freightItemFk, vClientFk) > 0
GROUP BY e.freightItemFk);
IF(vHasDailyInvoice) AND vHasToInvoice THEN
-- Facturacion rapida
@ -89,10 +89,10 @@ BEGIN
-- Facturar si está contabilizado
IF vIsTaxDataChecked THEN
CALL invoiceOut_newFromClient(
vClientFk,
(SELECT invoiceSerial(vClientFk, vCompanyFk, 'M')),
vShipped,
vCompanyFk,
vClientFk,
(SELECT invoiceSerial(vClientFk, vCompanyFk, 'multiple')),
vShipped,
vCompanyFk,
NULL,
NULL,
vNewInvoiceId);

View File

@ -14,16 +14,28 @@ BEGIN
DECLARE vTicketFk INT;
DECLARE cTickets CURSOR FOR
SELECT id FROM ticket
WHERE refFk IS NULL
AND ((vScope = 'client' AND clientFk = vId)
OR (vScope = 'address' AND addressFk = vId));
SELECT DISTINCT t.id
FROM ticket t
LEFT JOIN tItems ti ON ti.id = t.id
WHERE t.refFk IS NULL
AND ((vScope = 'client' AND t.clientFk = vId)
OR (vScope = 'address' AND t.addressFk = vId)
OR (vScope = 'item' AND ti.id)
);
DECLARE CONTINUE HANDLER FOR NOT FOUND
SET vDone = TRUE;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET vDone = TRUE;
CREATE OR REPLACE TEMPORARY TABLE tItems
(PRIMARY KEY (id))
ENGINE = MEMORY
SELECT DISTINCT t.id
FROM ticket t
JOIN sale s ON s.ticketFk = t.id
JOIN itemTaxCountry itc ON itc.itemFk = s.itemFk
WHERE t.refFk IS NULL
AND (vScope = 'item' AND itc.itemFk = vId);
OPEN cTickets;
myLoop: LOOP
SET vDone = FALSE;
FETCH cTickets INTO vTicketFk;
@ -34,7 +46,8 @@ BEGIN
CALL ticket_recalc(vTicketFk, NULL);
END LOOP;
CLOSE cTickets;
DROP TEMPORARY TABLE tItems;
END$$
DELIMITER ;

View File

@ -0,0 +1,8 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `vn`.`host_beforeInsert`
BEFORE INSERT ON `host`
FOR EACH ROW
BEGIN
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -4,5 +4,6 @@ CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `vn`.`host_beforeUpdate`
FOR EACH ROW
BEGIN
SET new.updated = util.VN_NOW();
SET NEW.editorFk = account.myUser_getId();
END$$
DELIMITER ;

View File

@ -0,0 +1,12 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `vn`.`roadmap_beforeInsert`
BEFORE INSERT ON `roadmap`
FOR EACH ROW
BEGIN
IF NEW.driver1Fk IS NOT NULL THEN
SET NEW.driverName = (SELECT firstName FROM worker WHERE id = NEW.driver1Fk);
ELSE
SET NEW.driverName = NULL;
END IF;
END$$
DELIMITER ;

View File

@ -0,0 +1,12 @@
DELIMITER $$
CREATE OR REPLACE DEFINER=`root`@`localhost` TRIGGER `vn`.`roadmap_beforeUpdate`
BEFORE UPDATE ON `roadmap`
FOR EACH ROW
BEGIN
IF NEW.driver1Fk IS NOT NULL THEN
SET NEW.driverName = (SELECT firstName FROM worker WHERE id = NEW.driver1Fk);
ELSE
SET NEW.driverName = NULL;
END IF;
END$$
DELIMITER ;

View File

@ -2,5 +2,5 @@ CREATE OR REPLACE DEFINER=`root`@`localhost`
SQL SECURITY DEFINER
VIEW `vn2008`.`mandato_tipo`
AS SELECT `m`.`id` AS `idmandato_tipo`,
`m`.`name` AS `Nombre`
`m`.`code` AS `Nombre`
FROM `vn`.`mandateType` `m`

View File

@ -0,0 +1 @@
ALTER TABLE srt.moving DROP INDEX moving_fk1_idx;

View File

@ -0,0 +1,4 @@
ALTER TABLE vn.invoiceOutSerial
MODIFY COLUMN `type` enum('global','quick','multiple') CHARACTER SET utf8mb3 COLLATE utf8mb3_unicode_ci DEFAULT NULL NULL;
CREATE UNIQUE INDEX invoiceOutSerial_taxAreaFk_IDX USING BTREE ON vn.invoiceOutSerial (taxAreaFk,`type`);

View File

@ -0,0 +1,3 @@
UPDATE vn.invoiceOutSerial
SET `type`='multiple'
WHERE `description` LIKE '%Múltiple%';

View File

@ -0,0 +1,3 @@
ALTER TABLE vn.productionConfig
DROP COLUMN scannableCodeType,
DROP COLUMN scannablePreviusCodeType;

View File

@ -0,0 +1,6 @@
-- Place your SQL code here
ALTER TABLE vn.packingSite DROP COLUMN IF EXISTS hasNewLabelMrwMethod;
ALTER TABLE vn.productionConfig ADD IF NOT EXISTS hasNewLabelMrwMethod BOOL DEFAULT TRUE NOT NULL
COMMENT 'column to activate the new mrw integration';

View File

@ -0,0 +1,3 @@
ALTER TABLE vn.operator
ADD COLUMN sizeLimit int(10) unsigned DEFAULT 90 NULL COMMENT 'Límite de altura en una colección para la asignación de pedidos' AFTER volumeLimit,
MODIFY COLUMN linesLimit int(10) unsigned DEFAULT 20 NULL COMMENT 'Límite de lineas en una colección para la asignación de pedidos';

View File

@ -0,0 +1 @@
ALTER TABLE vn.ticket DROP FOREIGN KEY ticket_FK;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOut DROP KEY Id_Factura;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOut MODIFY COLUMN id int(10) unsigned NOT NULL;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceCorrection DROP FOREIGN KEY corrected_fk;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceCorrection DROP FOREIGN KEY correcting_fk;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOutExpense DROP FOREIGN KEY invoiceOutExpence_FK_1;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOutTax DROP FOREIGN KEY invoiceOutFk;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOut DROP PRIMARY KEY;

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOut ADD CONSTRAINT invoiceOut_pk PRIMARY KEY (id);

View File

@ -0,0 +1 @@
ALTER TABLE vn.invoiceOut ADD CONSTRAINT invoiceOut_unique UNIQUE KEY (`ref`);

View File

@ -0,0 +1,5 @@
UPDATE vn.invoiceOut
SET id = (SELECT MAX(id) + 1 FROM vn.invoiceOut)
WHERE id = 0;
ALTER TABLE vn.invoiceOut MODIFY COLUMN id int(10) unsigned auto_increment NOT NULL;

View File

@ -0,0 +1,2 @@
ALTER TABLE vn.ticket ADD CONSTRAINT ticket_invoiceOut_FK
FOREIGN KEY (refFk) REFERENCES vn.invoiceOut(`ref`) ON DELETE RESTRICT ON UPDATE CASCADE;

View File

@ -0,0 +1,2 @@
ALTER TABLE vn.invoiceCorrection ADD CONSTRAINT invoiceCorrection_invoiceOut_FK
FOREIGN KEY (correctingFk) REFERENCES vn.invoiceOut(id) ON DELETE CASCADE ON UPDATE CASCADE;

View File

@ -0,0 +1,2 @@
ALTER TABLE vn.invoiceCorrection ADD CONSTRAINT invoiceCorrection_invoiceOut_FK_1
FOREIGN KEY (correctedFk) REFERENCES vn.invoiceOut(id) ON DELETE CASCADE ON UPDATE CASCADE;

View File

@ -0,0 +1,2 @@
ALTER TABLE vn.invoiceOutExpense ADD CONSTRAINT invoiceOutExpense_invoiceOut_FK
FOREIGN KEY (invoiceOutFk) REFERENCES vn.invoiceOut(id) ON DELETE CASCADE ON UPDATE CASCADE;

View File

@ -0,0 +1,2 @@
ALTER TABLE vn.invoiceOutTax ADD CONSTRAINT invoiceOutTax_invoiceOut_FK
FOREIGN KEY (invoiceOutFk) REFERENCES vn.invoiceOut(id) ON DELETE CASCADE ON UPDATE CASCADE;

View File

@ -0,0 +1,8 @@
USE vn;
CREATE TABLE IF NOT EXISTS ormConfig (
id int(5) NOT NULL AUTO_INCREMENT primary key,
selectLimit int(5) NOT NULL
);
INSERT IGNORE INTO ormConfig SET selectLimit = 1000;

View File

@ -0,0 +1,2 @@
-- Place your SQL code here
ALTER TABLE vn.invoiceInConfig ADD balanceStartingDate DATE DEFAULT '2015-01-01' NOT NULL;

View File

@ -0,0 +1,2 @@
ALTER TABLE bs.waste CHANGE saleQuantity saleWasteQuantity decimal(10,2) DEFAULT NULL NULL AFTER saleTotal;
ALTER TABLE bs.waste MODIFY COLUMN saleTotal decimal(10,2) DEFAULT NULL NULL COMMENT 'Coste';

View File

@ -0,0 +1 @@
DROP TABLE bi.Greuges_comercial_detail;

View File

@ -0,0 +1 @@
ALTER TABLE vn.host ADD editorFk int(10) unsigned DEFAULT NULL NULL;

View File

@ -0,0 +1,3 @@
ALTER TABLE vn.item
ADD CONSTRAINT item_itemPackingType_FK FOREIGN KEY (itemPackingTypeFk)
REFERENCES vn.itemPackingType(code) ON DELETE RESTRICT ON UPDATE CASCADE;

View File

@ -0,0 +1,9 @@
ALTER TABLE hedera.tpvMerchantEnable
DROP FOREIGN KEY tpvMerchantEnable_ibfk_1,
DROP PRIMARY KEY,
ADD CONSTRAINT tpvMerchantEnable_pk PRIMARY KEY (merchantFk),
ADD CONSTRAINT tpvMerchantEnable_tpvMerchant_FK
FOREIGN KEY (merchantFk)
REFERENCES hedera.tpvMerchant(id)
ON DELETE RESTRICT
ON UPDATE CASCADE;

View File

@ -0,0 +1,3 @@
ALTER TABLE vn.mandateType
CHANGE name code VARCHAR(45) NOT NULL,
ADD UNIQUE (code);

View File

@ -0,0 +1,3 @@
ALTER TABLE vn.accountDetailType
ADD COLUMN code VARCHAR(45),
ADD UNIQUE (code);

View File

@ -0,0 +1,9 @@
UPDATE vn.accountDetailType
SET code = CASE description
WHEN 'IBAN' THEN 'iban'
WHEN 'SWIFT' THEN 'swift'
WHEN 'Referencia Remesas' THEN 'remRef'
WHEN 'Referencia Transferencias' THEN 'trnRef'
WHEN 'Referencia Nominas' THEN 'payRef'
WHEN 'ABA' THEN 'aba'
END;

View File

@ -0,0 +1,3 @@
ALTER TABLE hedera.tpvMerchantEnable
MODIFY COLUMN companyFk int(10) unsigned NOT NULL,
ADD CONSTRAINT tpvMerchantEnable_company_FK FOREIGN KEY (companyFk) REFERENCES vn.company(id) ON DELETE RESTRICT ON UPDATE CASCADE;

View File

@ -0,0 +1,19 @@
CREATE OR REPLACE TABLE `srt`.`bufferLog` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`originFk` int(11) DEFAULT NULL,
`userFk` int(10) unsigned DEFAULT NULL,
`action` set('insert','update','delete','select') NOT NULL,
`creationDate` timestamp NULL DEFAULT current_timestamp(),
`description` text CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci DEFAULT NULL,
`changedModel` enum('Buffer', 'Config') NOT NULL DEFAULT 'Buffer',
`oldInstance` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`oldInstance`)),
`newInstance` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`newInstance`)),
`changedModelId` int(11) NOT NULL,
`changedModelValue` varchar(45) DEFAULT NULL,
`summaryId` varchar(30) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `logBufferUserFk` (`userFk`),
KEY `bufferLog_changedModel` (`changedModel`,`changedModelId`,`creationDate`),
KEY `bufferLog_originFk` (`originFk`,`creationDate`),
CONSTRAINT `bufferUserFk` FOREIGN KEY (`userFk`) REFERENCES `account`.`user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb3 COLLATE=utf8mb3_unicode_ci;

View File

@ -0,0 +1 @@
ALTER TABLE srt.buffer ADD editorFk int(10) unsigned DEFAULT NULL NULL;

View File

@ -0,0 +1 @@
ALTER TABLE srt.config ADD editorFk int(10) unsigned DEFAULT NULL NULL;

View File

@ -0,0 +1,9 @@
CREATE TABLE vn.quadMindsApiConfig (
id int(10) unsigned NULL PRIMARY KEY,
`url` varchar(255) DEFAULT NULL NULL,
`key` varchar(255) DEFAULT NULL NULL,
CONSTRAINT quadMindsConfig_check CHECK (id = 1)
)
ENGINE=InnoDB
DEFAULT CHARSET=utf8mb3
COLLATE=utf8mb3_unicode_ci;

View File

@ -0,0 +1,6 @@
ALTER TABLE vn.roadmap
ADD COLUMN m3 INT UNSIGNED NULL,
ADD COLUMN driver2Fk INT UNSIGNED NULL,
ADD COLUMN driver1Fk INT UNSIGNED NULL,
ADD CONSTRAINT roadmap_worker_FK FOREIGN KEY (driver1Fk) REFERENCES vn.worker(id) ON DELETE RESTRICT ON UPDATE CASCADE,
ADD CONSTRAINT roadmap_worker_FK_2 FOREIGN KEY (driver2Fk) REFERENCES vn.worker(id) ON DELETE RESTRICT ON UPDATE CASCADE;

View File

@ -0,0 +1,24 @@
DELETE FROM `salix`.`ACL`
WHERE `model` = 'Ticket'
AND `property` = 'refund'
AND `accessType` = 'WRITE'
AND `permission` = 'ALLOW'
AND `principalType` = 'ROLE'
AND `principalId` = 'salesAssistant';
UPDATE `salix`.`ACL`
SET `property` = 'cloneAll'
WHERE `model` = 'Ticket'
AND `property` = 'refund'
AND `accessType` = 'WRITE'
AND `permission` = 'ALLOW'
AND `principalType` = 'ROLE'
AND `principalId` IN ('invoicing', 'claimManager', 'logistic');
DELETE FROM `salix`.`ACL`
WHERE `model` = 'Ticket'
AND `property` = 'clone'
AND `accessType` = 'WRITE'
AND `permission` = 'ALLOW'
AND `principalType` = 'ROLE'
AND `principalId` = 'administrative';

View File

@ -0,0 +1,4 @@
-- Place your SQL code here
ALTER TABLE vn.saleGroup ADD stateFk TINYINT(3) UNSIGNED;
ALTER TABLE vn.saleGroup ADD CONSTRAINT saleGroup_state_FK FOREIGN KEY (stateFk) REFERENCES vn.state(id) ON DELETE RESTRICT ON UPDATE CASCADE;

View File

@ -738,69 +738,6 @@ export default {
worker: 'vn-worker-autocomplete[ng-model="$ctrl.userFk"]',
saveStateButton: `button[type=submit]`
},
claimsIndex: {
searchResult: 'vn-claim-index vn-card > vn-table > div > vn-tbody > a'
},
claimDescriptor: {
moreMenu: 'vn-claim-descriptor vn-icon-button[icon=more_vert]',
moreMenuDeleteClaim: '.vn-menu [name="deleteClaim"]',
acceptDeleteClaim: '.vn-confirm.shown button[response="accept"]'
},
claimSummary: {
header: 'vn-claim-summary > vn-card > h5',
state: 'vn-claim-summary vn-label-value[label="State"] > section > span',
observation: 'vn-claim-summary vn-horizontal.text',
firstSaleItemId: 'vn-claim-summary vn-horizontal > vn-auto:nth-child(5) vn-table > div > vn-tbody > vn-tr:nth-child(1) > vn-td:nth-child(1) > span',
firstSaleDescriptorImage: '.vn-popover.shown vn-item-descriptor img',
itemDescriptorPopover: '.vn-popover.shown vn-item-descriptor',
itemDescriptorPopoverItemDiaryButton: '.vn-popover vn-item-descriptor vn-quick-link[icon="icon-transaction"] > a',
firstDevelopmentWorker: 'vn-claim-summary vn-horizontal > vn-auto:nth-child(4) vn-table > div > vn-tbody > vn-tr:nth-child(1) > vn-td:nth-child(4) > span',
firstDevelopmentWorkerGoToClientButton: '.vn-popover vn-worker-descriptor vn-quick-link[icon="person"] > a',
firstActionTicketId: 'vn-claim-summary > vn-card > vn-horizontal > vn-auto:nth-child(5) vn-table > div > vn-tbody > vn-tr > vn-td:nth-child(2) > span',
firstActionTicketDescriptor: '.vn-popover.shown vn-ticket-descriptor'
},
claimBasicData: {
claimState: 'vn-claim-basic-data vn-autocomplete[ng-model="$ctrl.claim.claimStateFk"]',
packages: 'vn-input-number[ng-model="$ctrl.claim.packages"]',
saveButton: `button[type=submit]`
},
claimDetail: {
secondItemDiscount: 'vn-claim-detail > vn-vertical > vn-card > vn-vertical > vn-table > div > vn-tbody > vn-tr:nth-child(2) > vn-td:nth-child(6) > span',
discount: '.vn-popover.shown vn-input-number[ng-model="$ctrl.newDiscount"]',
discoutPopoverMana: '.vn-popover.shown .content > div > vn-horizontal > h5',
addItemButton: 'vn-claim-detail a vn-float-button',
firstClaimableSaleFromTicket: '.vn-dialog.shown vn-tbody > vn-tr',
claimDetailLine: 'vn-claim-detail > vn-vertical > vn-card > vn-vertical > vn-table > div > vn-tbody > vn-tr',
totalClaimed: 'vn-claim-detail > vn-vertical > vn-card > vn-vertical > vn-horizontal > div > vn-label-value:nth-child(2) > section > span',
secondItemDeleteButton: 'vn-claim-detail > vn-vertical > vn-card > vn-vertical > vn-table > div > vn-tbody > vn-tr:nth-child(2) > vn-td:nth-child(8) > vn-icon-button > button > vn-icon > i'
},
claimDevelopment: {
addDevelopmentButton: 'vn-claim-development > vn-vertical > vn-card > vn-vertical > vn-one > vn-icon-button > button > vn-icon',
firstDeleteDevelopmentButton: 'vn-claim-development > vn-vertical > vn-card > vn-vertical > form > vn-horizontal:nth-child(2) > vn-icon-button > button > vn-icon',
firstClaimReason: 'vn-claim-development vn-horizontal:nth-child(1) vn-autocomplete[ng-model="claimDevelopment.claimReasonFk"]',
firstClaimResult: 'vn-claim-development vn-horizontal:nth-child(1) vn-autocomplete[ng-model="claimDevelopment.claimResultFk"]',
firstClaimResponsible: 'vn-claim-development vn-horizontal:nth-child(1) vn-autocomplete[ng-model="claimDevelopment.claimResponsibleFk"]',
firstClaimWorker: 'vn-claim-development vn-horizontal:nth-child(1) vn-worker-autocomplete[ng-model="claimDevelopment.workerFk"]',
firstClaimRedelivery: 'vn-claim-development vn-horizontal:nth-child(1) vn-autocomplete[ng-model="claimDevelopment.claimRedeliveryFk"]',
secondClaimReason: 'vn-claim-development vn-horizontal:nth-child(2) vn-autocomplete[ng-model="claimDevelopment.claimReasonFk"]',
secondClaimResult: 'vn-claim-development vn-horizontal:nth-child(2) vn-autocomplete[ng-model="claimDevelopment.claimResultFk"]',
secondClaimResponsible: 'vn-claim-development vn-horizontal:nth-child(2) vn-autocomplete[ng-model="claimDevelopment.claimResponsibleFk"]',
secondClaimWorker: 'vn-claim-development vn-horizontal:nth-child(2) vn-worker-autocomplete[ng-model="claimDevelopment.workerFk"]',
secondClaimRedelivery: 'vn-claim-development vn-horizontal:nth-child(2) vn-autocomplete[ng-model="claimDevelopment.claimRedeliveryFk"]',
saveDevelopmentButton: 'button[type=submit]'
},
claimNote: {
addNoteFloatButton: 'vn-float-button',
note: 'vn-textarea[ng-model="$ctrl.note.text"]',
saveButton: 'button[type=submit]',
firstNoteText: 'vn-claim-note .text'
},
claimAction: {
importClaimButton: 'vn-claim-action vn-button[label="Import claim"]',
anyLine: 'vn-claim-action vn-tbody > vn-tr',
firstDeleteLine: 'vn-claim-action tr:nth-child(2) vn-icon-button[icon="delete"]',
isPaidWithManaCheckbox: 'vn-claim-action vn-check[ng-model="$ctrl.claim.isChargedToMana"]'
},
ordersIndex: {
secondSearchResultTotal: 'vn-order-index vn-card > vn-table > div > vn-tbody .vn-tr:nth-child(2) vn-td:nth-child(9)',
advancedSearchButton: 'vn-order-search-panel vn-submit[label="Search"]',

View File

@ -1,29 +0,0 @@
import selectors from '../../../helpers/selectors.js';
import getBrowser from '../../../helpers/puppeteer';
describe('department summary path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
await page.accessToSection('worker.department');
await page.doSearch('INFORMATICA');
await page.click(selectors.department.firstDepartment);
});
afterAll(async() => {
await browser.close();
});
it('should reach the employee summary section and check all properties', async() => {
expect(await page.waitToGetProperty(selectors.departmentSummary.header, 'innerText')).toEqual('INFORMATICA');
expect(await page.getProperty(selectors.departmentSummary.name, 'innerText')).toEqual('INFORMATICA');
expect(await page.getProperty(selectors.departmentSummary.code, 'innerText')).toEqual('it');
expect(await page.getProperty(selectors.departmentSummary.chat, 'innerText')).toEqual('informatica-cau');
expect(await page.getProperty(selectors.departmentSummary.bossDepartment, 'innerText')).toEqual('');
expect(await page.getProperty(selectors.departmentSummary.email, 'innerText')).toEqual('-');
expect(await page.getProperty(selectors.departmentSummary.clientFk, 'innerText')).toEqual('-');
});
});

View File

@ -1,43 +0,0 @@
import getBrowser from '../../../helpers/puppeteer';
import selectors from '../../../helpers/selectors.js';
const $ = {
form: 'vn-worker-department-basic-data form',
};
describe('department summary path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
await page.accessToSection('worker.department');
await page.doSearch('INFORMATICA');
await page.click(selectors.department.firstDepartment);
});
beforeEach(async() => {
await page.accessToSection('worker.department.card.basicData');
});
afterAll(async() => {
await browser.close();
});
it(`should edit the department basic data and confirm the department data was edited`, async() => {
const values = {
Name: 'Informatica',
Code: 'IT',
Chat: 'informatica-cau',
Email: 'it@verdnatura.es',
};
await page.fillForm($.form, values);
const formValues = await page.fetchForm($.form, Object.keys(values));
const message = await page.sendForm($.form, values);
expect(message.isSuccess).toBeTrue();
expect(formValues).toEqual(values);
});
});

View File

@ -1,34 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker summary path', () => {
const workerId = 3;
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('employee', 'worker');
const httpDataResponse = page.waitForResponse(response => {
return response.status() === 200 && response.url().includes(`Workers/${workerId}`);
});
await page.accessToSearchResult('agencyNick');
await httpDataResponse;
});
afterAll(async() => {
await browser.close();
});
it('should reach the employee summary section and check all properties', async() => {
expect(await page.getProperty(selectors.workerSummary.header, 'innerText')).toEqual('agency agency');
expect(await page.getProperty(selectors.workerSummary.id, 'innerText')).toEqual('3');
expect(await page.getProperty(selectors.workerSummary.email, 'innerText')).toEqual('agency@verdnatura.es');
expect(await page.getProperty(selectors.workerSummary.department, 'innerText')).toEqual('CAMARA');
expect(await page.getProperty(selectors.workerSummary.userId, 'innerText')).toEqual('3');
expect(await page.getProperty(selectors.workerSummary.userName, 'innerText')).toEqual('agency');
expect(await page.getProperty(selectors.workerSummary.role, 'innerText')).toEqual('agency');
expect(await page.getProperty(selectors.workerSummary.extension, 'innerText')).toEqual('1101');
expect(await page.getProperty(selectors.workerSummary.locker, 'innerText')).toEqual('-');
});
});

View File

@ -1,40 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker basic data path', () => {
const workerId = 1106;
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
const httpDataResponse = page.waitForResponse(response => {
return response.status() === 200 && response.url().includes(`Workers/${workerId}`);
});
await page.accessToSearchResult('David Charles Haller');
await httpDataResponse;
await page.accessToSection('worker.card.basicData');
});
afterAll(async() => {
await browser.close();
});
it('should edit the form and then reload the section and check the data was edited', async() => {
await page.overwrite(selectors.workerBasicData.name, 'David C.');
await page.overwrite(selectors.workerBasicData.surname, 'H.');
await page.overwrite(selectors.workerBasicData.phone, '444332211');
await page.click(selectors.workerBasicData.saveButton);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
await page.reloadSection('worker.card.basicData');
expect(await page.waitToGetProperty(selectors.workerBasicData.name, 'value')).toEqual('David C.');
expect(await page.waitToGetProperty(selectors.workerBasicData.surname, 'value')).toEqual('H.');
expect(await page.waitToGetProperty(selectors.workerBasicData.phone, 'value')).toEqual('444332211');
});
});

View File

@ -1,32 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker pbx path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
await page.accessToSearchResult('employee');
await page.accessToSection('worker.card.pbx');
});
afterAll(async() => {
await browser.close();
});
it('should receive an error when the extension exceeds 4 characters and then sucessfully save the changes', async() => {
await page.write(selectors.workerPbx.extension, '55555');
await page.click(selectors.workerPbx.saveButton);
let message = await page.waitForSnackbar();
expect(message.text).toContain('Extension format is invalid');
await page.overwrite(selectors.workerPbx.extension, '4444');
await page.click(selectors.workerPbx.saveButton);
message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved! User must access web');
});
});

View File

@ -1,65 +0,0 @@
/* eslint max-len: ["error", { "code": 150 }]*/
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker time control path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('salesBoss', 'worker');
await page.accessToSearchResult('HankPym');
await page.accessToSection('worker.card.timeControl');
});
afterAll(async() => {
await browser.close();
});
const eightAm = '08:00';
const fourPm = '16:00';
const hankPymId = 1107;
it('should go to the next month, go to current month and go 1 month in the past', async() => {
let date = Date.vnNew();
date.setDate(1);
date.setMonth(date.getMonth() + 1);
let month = date.toLocaleString('default', {month: 'long'});
await page.waitToClick(selectors.workerTimeControl.nextMonthButton);
let result = await page.getProperty(selectors.workerTimeControl.monthName, 'innerText');
expect(result).toContain(month);
date = Date.vnNew();
date.setDate(1);
month = date.toLocaleString('default', {month: 'long'});
await page.waitToClick(selectors.workerTimeControl.previousMonthButton);
result = await page.getProperty(selectors.workerTimeControl.monthName, 'innerText');
expect(result).toContain(month);
date = Date.vnNew();
date.setDate(1);
date.setMonth(date.getMonth() - 1);
const timestamp = Math.round(date.getTime() / 1000);
month = date.toLocaleString('default', {month: 'long'});
await page.loginAndModule('salesBoss', 'worker');
await page.goto(`http://localhost:5000/#!/worker/${hankPymId}/time-control?timestamp=${timestamp}`);
await page.waitToClick(selectors.workerTimeControl.secondWeekDay);
result = await page.getProperty(selectors.workerTimeControl.monthName, 'innerText');
expect(result).toContain(month);
});
it('should change week of month', async() => {
await page.click(selectors.workerTimeControl.thrirdWeekDay);
const result = await page.getProperty(selectors.workerTimeControl.mondayWorkedHours, 'innerText');
expect(result).toEqual('00:00 h.');
});
});

View File

@ -1,114 +0,0 @@
/* eslint-disable max-len */
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker calendar path', () => {
const reasonableTimeBetweenClicks = 300;
const date = Date.vnNew();
const lastYear = (date.getFullYear() - 1).toString();
let browser;
let page;
async function accessAs(user) {
await page.loginAndModule(user, 'worker');
await page.accessToSearchResult('Charles Xavier');
await page.accessToSection('worker.card.calendar');
}
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
accessAs('hr');
});
afterAll(async() => {
await browser.close();
});
describe('as hr', () => {
it('should set two days as holidays on the calendar and check the total holidays increased by 1.5', async() => {
await page.waitToClick(selectors.workerCalendar.holidays);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.penultimateMondayOfJanuary);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.absence);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.lastMondayOfMarch);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.halfHoliday);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.fistMondayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.furlough);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.secondTuesdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.secondWednesdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.secondThursdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.halfFurlough);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.secondFridayOfJun);
expect(await page.getProperty(selectors.workerCalendar.totalHolidaysUsed, 'innerText')).toContain(' 1.5 ');
});
});
describe(`as salesBoss`, () => {
it(`should log in, get to Charles Xavier's calendar, undo what was done here, and check the total holidays used are back to what it was`, async() => {
accessAs('salesBoss');
await page.waitToClick(selectors.workerCalendar.holidays);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.penultimateMondayOfJanuary);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.absence);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.lastMondayOfMarch);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.halfHoliday);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.fistMondayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.furlough);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.secondTuesdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.secondWednesdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.secondThursdayOfMay);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.halfFurlough);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.waitToClick(selectors.workerCalendar.secondFridayOfJun);
expect(await page.getProperty(selectors.workerCalendar.totalHolidaysUsed, 'innerText')).toContain(' 0 ');
});
});
describe(`as Charles Xavier`, () => {
it('should log in and get to his calendar, make a futile attempt to add holidays, check the total holidays used are now the initial ones and use the year selector to go to the previous year', async() => {
accessAs('CharlesXavier');
await page.waitToClick(selectors.workerCalendar.holidays);
await page.waitForTimeout(reasonableTimeBetweenClicks);
await page.click(selectors.workerCalendar.penultimateMondayOfJanuary);
expect(await page.getProperty(selectors.workerCalendar.totalHolidaysUsed, 'innerText')).toContain(' 0 ');
await page.autocompleteSearch(selectors.workerCalendar.year, lastYear);
expect(await page.getProperty(selectors.workerCalendar.totalHolidaysUsed, 'innerText')).toContain(' 0 ');
});
});
});

View File

@ -1,73 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Worker create path', () => {
let browser;
let page;
let newWorker;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
await page.waitToClick(selectors.workerCreate.newWorkerButton);
await page.waitForState('worker.create');
});
afterAll(async() => {
await browser.close();
});
it('should insert default data', async() => {
await page.write(selectors.workerCreate.firstname, 'Victor');
await page.write(selectors.workerCreate.lastname, 'Von Doom');
await page.write(selectors.workerCreate.fi, '78457139E');
await page.write(selectors.workerCreate.phone, '12356789');
await page.write(selectors.workerCreate.postcode, '46680');
await page.write(selectors.workerCreate.street, 'S/ DOOMSTADT');
await page.write(selectors.workerCreate.email, 'doctorDoom@marvel.com');
await page.write(selectors.workerCreate.iban, 'ES9121000418450200051332');
// should check for autocompleted worker code and worker user name
const workerCode = await page
.waitToGetProperty(selectors.workerCreate.code, 'value');
newWorker = await page
.waitToGetProperty(selectors.workerCreate.user, 'value');
expect(workerCode).toEqual('VVD');
expect(newWorker).toContain('victorvd');
// should fail if necessary data is void
await page.waitToClick(selectors.workerCreate.createButton);
let message = await page.waitForSnackbar();
expect(message.text).toContain('is a required argument');
// should create a new worker and go to worker basic data'
await page.pickDate(selectors.workerCreate.birth, new Date(1962, 8, 5));
await page.autocompleteSearch(selectors.workerCreate.boss, 'deliveryAssistant');
await page.waitToClick(selectors.workerCreate.createButton);
message = await page.waitForSnackbar();
await page.waitForState('worker.card.basicData');
expect(message.text).toContain('Data saved!');
// 'rollback'
await page.loginAndModule('itManagement', 'account');
await page.accessToSearchResult(newWorker);
await page.waitToClick(selectors.accountDescriptor.menuButton);
await page.waitToClick(selectors.accountDescriptor.deactivateUser);
await page.waitToClick(selectors.accountDescriptor.acceptButton);
message = await page.waitForSnackbar();
expect(message.text).toContain('User deactivated!');
await page.waitToClick(selectors.accountDescriptor.menuButton);
await page.waitToClick(selectors.accountDescriptor.disableAccount);
await page.waitToClick(selectors.accountDescriptor.acceptButton);
message = await page.waitForSnackbar();
expect(message.text).toContain('Account disabled!');
});
});

View File

@ -1,42 +0,0 @@
import selectors from '../../helpers/selectors';
import getBrowser from '../../helpers/puppeteer';
describe('Worker Add notes path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('hr', 'worker');
await page.accessToSearchResult('Bruce Banner');
await page.accessToSection('worker.card.note.index');
});
afterAll(async() => {
await browser.close();
});
it(`should reach the notes index`, async() => {
await page.waitForState('worker.card.note.index');
});
it(`should click on the add note button`, async() => {
await page.waitToClick(selectors.workerNotes.addNoteFloatButton);
await page.waitForState('worker.card.note.create');
});
it(`should create a note`, async() => {
await page.waitForSelector(selectors.workerNotes.note);
await page.type(`${selectors.workerNotes.note} textarea`, 'Meeting with Black Widow 21st 9am');
await page.waitToClick(selectors.workerNotes.saveButton);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
it('should confirm the note was created', async() => {
const result = await page.waitToGetProperty(selectors.workerNotes.firstNoteText, 'innerText');
expect(result).toEqual('Meeting with Black Widow 21st 9am');
});
});

View File

@ -19,7 +19,9 @@ describe('Ticket Edit sale path', () => {
it(`should click on the first sale claim icon to navigate over there`, async() => {
await page.waitToClick(selectors.ticketSales.firstSaleClaimIcon);
await page.waitForState('claim.card.basicData');
await page.waitForNavigation();
await page.goBack();
await page.goBack();
});
it('should navigate to the tickets index', async() => {
@ -243,29 +245,13 @@ describe('Ticket Edit sale path', () => {
await page.waitToClick(selectors.ticketSales.moreMenu);
await page.waitToClick(selectors.ticketSales.moreMenuCreateClaim);
await page.waitToClick(selectors.globalItems.acceptButton);
await page.waitForState('claim.card.basicData');
});
it('should click on the Claims button of the top bar menu', async() => {
await page.waitToClick(selectors.globalItems.applicationsMenuButton);
await page.waitForSelector(selectors.globalItems.applicationsMenuVisible);
await page.waitToClick(selectors.globalItems.claimsButton);
await page.waitForState('claim.index');
});
it('should search for the claim with id 4', async() => {
await page.accessToSearchResult('4');
await page.waitForState('claim.card.summary');
});
it('should click the Tickets button of the top bar menu', async() => {
await page.waitToClick(selectors.globalItems.applicationsMenuButton);
await page.waitForSelector(selectors.globalItems.applicationsMenuVisible);
await page.waitToClick(selectors.globalItems.ticketsButton);
await page.waitForState('ticket.index');
await page.waitForNavigation();
});
it('should search for a ticket then access to the sales section', async() => {
await page.goBack();
await page.goBack();
await page.loginAndModule('salesPerson', 'ticket');
await page.accessToSearchResult('16');
await page.accessToSection('ticket.card.sale');
});

View File

@ -1,61 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer';
describe('Claim edit basic data path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
});
afterAll(async() => {
await browser.close();
});
it(`should log in as claimManager then reach basic data of the target claim`, async() => {
await page.loginAndModule('claimManager', 'claim');
await page.accessToSearchResult('1');
await page.accessToSection('claim.card.basicData');
});
it(`should edit claim state and observation fields`, async() => {
await page.autocompleteSearch(selectors.claimBasicData.claimState, 'Resuelto');
await page.clearInput(selectors.claimBasicData.packages);
await page.write(selectors.claimBasicData.packages, '2');
await page.waitToClick(selectors.claimBasicData.saveButton);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
it(`should have been redirected to the next section of claims as the role is claimManager`, async() => {
await page.waitForState('claim.card.detail');
});
it('should confirm the claim state was edited', async() => {
await page.reloadSection('claim.card.basicData');
await page.waitForSelector(selectors.claimBasicData.claimState);
const result = await page.waitToGetProperty(selectors.claimBasicData.claimState, 'value');
expect(result).toEqual('Resuelto');
});
it('should confirm the claim packages was edited', async() => {
const result = await page
.waitToGetProperty(selectors.claimBasicData.packages, 'value');
expect(result).toEqual('2');
});
it(`should edit the claim to leave it untainted`, async() => {
await page.autocompleteSearch(selectors.claimBasicData.claimState, 'Pendiente');
await page.clearInput(selectors.claimBasicData.packages);
await page.write(selectors.claimBasicData.packages, '0');
await page.waitToClick(selectors.claimBasicData.saveButton);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
});

View File

@ -1,54 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer.js';
describe('Claim action path', () => {
let browser;
let page;
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
await page.loginAndModule('claimManager', 'claim');
await page.accessToSearchResult('2');
await page.accessToSection('claim.card.action');
});
afterAll(async() => {
await browser.close();
});
it('should import the claim', async() => {
await page.waitToClick(selectors.claimAction.importClaimButton);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
it('should delete the first line', async() => {
await page.waitToClick(selectors.claimAction.firstDeleteLine);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
it('should refresh the view to check not have lines', async() => {
await page.reloadSection('claim.card.action');
const result = await page.countElement(selectors.claimAction.anyLine);
expect(result).toEqual(0);
});
it('should check the "is paid with mana" checkbox', async() => {
await page.waitToClick(selectors.claimAction.isPaidWithManaCheckbox);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Data saved!');
});
it('should confirm the "is paid with mana" is checked', async() => {
await page.reloadSection('claim.card.action');
const isPaidWithManaCheckbox = await page.checkboxState(selectors.claimAction.isPaidWithManaCheckbox);
expect(isPaidWithManaCheckbox).toBe('checked');
});
});

View File

@ -1,96 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer.js';
describe('Claim summary path', () => {
let browser;
let page;
const claimId = '4';
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
});
afterAll(async() => {
await browser.close();
});
it('should navigate to the target claim summary section', async() => {
await page.loginAndModule('salesPerson', 'claim');
await page.accessToSearchResult(claimId);
await page.waitForState('claim.card.summary');
});
it(`should display details from the claim and it's client on the top of the header`, async() => {
await page.waitForTextInElement(selectors.claimSummary.header, 'Tony Stark');
const result = await page.waitToGetProperty(selectors.claimSummary.header, 'innerText');
expect(result).toContain('4 -');
expect(result).toContain('Tony Stark');
});
it('should display the claim state', async() => {
const result = await page.waitToGetProperty(selectors.claimSummary.state, 'innerText');
expect(result).toContain('Resuelto');
});
it('should display the observation', async() => {
const result = await page.waitToGetProperty(selectors.claimSummary.observation, 'innerText');
expect(result).toContain('Wisi forensibus mnesarchum in cum. Per id impetus abhorreant');
});
it('should display the claimed line(s)', async() => {
const result = await page.waitToGetProperty(selectors.claimSummary.firstSaleItemId, 'innerText');
expect(result).toContain('2');
});
it(`should click on the first sale ID making the item descriptor visible`, async() => {
const firstItem = selectors.claimSummary.firstSaleItemId;
await page.evaluate(selectors => {
document.querySelector(selectors).scrollIntoView();
}, firstItem);
await page.click(firstItem);
await page.waitImgLoad(selectors.claimSummary.firstSaleDescriptorImage);
const visible = await page.isVisible(selectors.claimSummary.itemDescriptorPopover);
expect(visible).toBeTruthy();
});
it(`should check the url for the item diary link of the descriptor is for the right item id`, async() => {
await page.waitForSelector(selectors.claimSummary.itemDescriptorPopoverItemDiaryButton, {visible: true});
await page.closePopup();
});
it('should display the claim development details', async() => {
const result = await page.waitToGetProperty(selectors.claimSummary.firstDevelopmentWorker, 'innerText');
expect(result).toContain('salesAssistantNick');
});
it(`should click on the first development worker making the worker descriptor visible`, async() => {
await page.waitToClick(selectors.claimSummary.firstDevelopmentWorker);
const visible = await page.isVisible(selectors.claimSummary.firstDevelopmentWorkerGoToClientButton);
expect(visible).toBeTruthy();
});
it(`should check the url for the go to clientlink of the descriptor is for the right client id`, async() => {
await page.waitForSelector(selectors.claimSummary.firstDevelopmentWorkerGoToClientButton, {visible: true});
await page.closePopup();
});
it(`should click on the first action ticket ID making the ticket descriptor visible`, async() => {
await page.waitToClick(selectors.claimSummary.firstActionTicketId);
await page.waitForSelector(selectors.claimSummary.firstActionTicketDescriptor);
const visible = await page.isVisible(selectors.claimSummary.firstActionTicketDescriptor);
expect(visible).toBeTruthy();
});
});

View File

@ -1,58 +0,0 @@
import selectors from '../../helpers/selectors.js';
import getBrowser from '../../helpers/puppeteer.js';
describe('Claim descriptor path', () => {
let browser;
let page;
const claimId = '1';
beforeAll(async() => {
browser = await getBrowser();
page = browser.page;
});
afterAll(async() => {
await browser.close();
});
it('should now navigate to the target claim summary section', async() => {
await page.loginAndModule('salesPerson', 'claim');
await page.accessToSearchResult(claimId);
await page.waitForState('claim.card.summary');
});
it(`should not be able to see the delete claim button of the descriptor more menu`, async() => {
await page.waitToClick(selectors.claimDescriptor.moreMenu);
await page.waitForSelector(selectors.claimDescriptor.moreMenuDeleteClaim, {hidden: true});
});
it(`should log in as claimManager and navigate to the target claim`, async() => {
await page.loginAndModule('claimManager', 'claim');
await page.accessToSearchResult(claimId);
await page.waitForState('claim.card.summary');
});
it(`should be able to see the delete claim button of the descriptor more menu`, async() => {
await page.waitToClick(selectors.claimDescriptor.moreMenu);
await page.waitForSelector(selectors.claimDescriptor.moreMenuDeleteClaim, {visible: true});
});
it(`should delete the claim`, async() => {
await page.waitToClick(selectors.claimDescriptor.moreMenuDeleteClaim);
await page.waitToClick(selectors.claimDescriptor.acceptDeleteClaim);
const message = await page.waitForSnackbar();
expect(message.text).toContain('Claim deleted!');
});
it(`should have been relocated to the claim index`, async() => {
await page.waitForState('claim.index');
});
it(`should search for the deleted claim to find no results`, async() => {
await page.doSearch(claimId);
const nResults = await page.countElement(selectors.claimsIndex.searchResult);
expect(nResults).toEqual(0);
});
});

Some files were not shown because too many files have changed in this diff Show More