2018-01-29 11:37:54 +00:00
|
|
|
var UserError = require('../helpers').UserError;
|
|
|
|
var getFinalState = require('../helpers').getFinalState;
|
|
|
|
var isMultiple = require('../helpers').isMultiple;
|
|
|
|
|
|
|
|
module.exports = function(Self) {
|
|
|
|
// Methods
|
|
|
|
|
|
|
|
require('../methods/client/activate')(Self);
|
|
|
|
require('../methods/client/listAddresses')(Self);
|
|
|
|
require('../methods/client/card')(Self);
|
|
|
|
require('../methods/client/createWithUser')(Self);
|
|
|
|
require('../methods/client/listWorkers')(Self);
|
|
|
|
require('../methods/client/filter')(Self);
|
|
|
|
require('../methods/client/hasCustomerRole')(Self);
|
|
|
|
require('../methods/client/activeSalesPerson')(Self);
|
|
|
|
require('../methods/client/addressesPropagateRe')(Self);
|
|
|
|
|
|
|
|
// Validations
|
|
|
|
|
|
|
|
Self.validatesUniquenessOf('fi', {
|
|
|
|
message: 'El NIF/CIF debe ser único'
|
|
|
|
});
|
|
|
|
Self.validatesUniquenessOf('socialName', {
|
|
|
|
message: 'La razón social debe ser única'
|
|
|
|
});
|
|
|
|
Self.validatesFormatOf('postcode', {
|
|
|
|
message: 'El código postal solo debe contener números',
|
|
|
|
allowNull: true,
|
|
|
|
allowBlank: true,
|
|
|
|
with: /^\d+$/
|
|
|
|
});
|
|
|
|
Self.validatesFormatOf('email', {
|
|
|
|
message: 'Correo electrónico inválido',
|
|
|
|
allowNull: true,
|
|
|
|
allowBlank: true,
|
2018-02-28 11:07:56 +00:00
|
|
|
with: /^[\w|-|.]+@[\w|-]+(\.[\w|-]+)*(,[\w|-|.]+@[\w|-]+(\.[\w|-]+)*)*$/
|
2018-01-29 11:37:54 +00:00
|
|
|
});
|
|
|
|
Self.validatesLengthOf('postcode', {
|
|
|
|
allowNull: true,
|
|
|
|
allowBlank: true,
|
|
|
|
min: 3, max: 10
|
|
|
|
});
|
|
|
|
|
|
|
|
var validateIban = require('../validations/validateIban');
|
|
|
|
Self.validateBinded('iban', validateIban, {
|
2018-02-27 21:50:14 +00:00
|
|
|
message: 'El iban no tiene el formato correcto',
|
|
|
|
allowNull: true, // FIXME: Ignored by loopback when it's false
|
|
|
|
allowBlank: true
|
2018-01-29 11:37:54 +00:00
|
|
|
});
|
|
|
|
|
|
|
|
let validateDni = require('../validations/validateDni');
|
|
|
|
Self.validateBinded('fi', validateDni, {
|
|
|
|
message: 'DNI Incorrecto'
|
|
|
|
});
|
|
|
|
|
|
|
|
Self.validate('payMethod', hasSalesMan, {
|
|
|
|
message: 'No se puede cambiar la forma de pago si no hay comercial asignado'
|
|
|
|
});
|
|
|
|
function hasSalesMan(err) {
|
|
|
|
if (this.payMethod && !this.salesPerson)
|
|
|
|
err();
|
|
|
|
}
|
|
|
|
|
|
|
|
Self.validateAsync('payMethodFk', hasIban, {
|
|
|
|
message: 'El método de pago seleccionado requiere que se especifique el IBAN'
|
|
|
|
});
|
|
|
|
function hasIban(err, done) {
|
|
|
|
Self.app.models.PayMethod.findById(this.payMethodFk, (_, instance) => {
|
|
|
|
if (instance && instance.ibanRequired && !this.iban)
|
|
|
|
err();
|
|
|
|
done();
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
// Hooks
|
|
|
|
|
|
|
|
Self.observe('before save', async function(ctx) {
|
|
|
|
let changes = ctx.data || ctx.instance;
|
|
|
|
let finalState = getFinalState(ctx);
|
|
|
|
|
|
|
|
if (changes.salesPerson === null) {
|
|
|
|
changes.credit = 0;
|
|
|
|
changes.discount = 0;
|
|
|
|
changes.payMethodFk = 5; // Credit card
|
|
|
|
}
|
|
|
|
|
|
|
|
if (changes.payMethodFk !== undefined && changes.dueDay === undefined)
|
|
|
|
changes.dueDay = 5;
|
|
|
|
|
|
|
|
if (isMultiple(ctx)) return;
|
|
|
|
|
|
|
|
if (changes.isEqualizated || changes.fi !== undefined) {
|
|
|
|
let fiLetter = finalState.fi && finalState.fi.toUpperCase().charAt(0);
|
|
|
|
let canMarkEqualizationTax = fiLetter != 'A' && fiLetter != 'B';
|
|
|
|
|
|
|
|
if (finalState.isEqualizated && !canMarkEqualizationTax)
|
2018-01-29 18:57:00 +00:00
|
|
|
throw new UserError('Unable to mark the equivalence surcharge');
|
2018-01-29 11:37:54 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if (changes.credit !== undefined)
|
|
|
|
try {
|
|
|
|
await validateCreditChange(ctx, finalState);
|
|
|
|
} catch (e) {
|
2018-01-29 18:57:00 +00:00
|
|
|
throw new UserError('You are not allowed to change the credit');
|
2018-01-29 11:37:54 +00:00
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
async function validateCreditChange(ctx, finalState) {
|
|
|
|
let models = Self.app.models;
|
|
|
|
let userId = ctx.options.accessToken.userId;
|
|
|
|
let filter = {
|
|
|
|
fields: ['roleFk'],
|
|
|
|
where: {
|
|
|
|
maxAmount: {gt: ctx.data.credit}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
let limits = await models.ClientCreditLimit.find(filter);
|
|
|
|
|
|
|
|
if (limits.length == 0)
|
|
|
|
throw new Error('Credit limits not found');
|
|
|
|
|
|
|
|
// Si el usuario no tiene alguno de los roles no continua
|
|
|
|
|
|
|
|
let requiredRoles = [];
|
|
|
|
for (limit of limits)
|
|
|
|
requiredRoles.push(limit.roleFk);
|
|
|
|
|
|
|
|
let where = {
|
|
|
|
roleId: {inq: requiredRoles},
|
|
|
|
principalType: 'USER',
|
|
|
|
principalId: userId
|
|
|
|
};
|
|
|
|
let count = await models.RoleMapping.count(where);
|
|
|
|
|
|
|
|
if (count <= 0)
|
|
|
|
throw new Error('The role cannot set this credit amount');
|
|
|
|
|
|
|
|
// Si se puso a 0 por gerencia, solo gerencia puede aumentarlo
|
|
|
|
|
|
|
|
let query = 'SELECT * FROM clientCredit WHERE clientFk = ? ORDER BY created DESC LIMIT 1';
|
|
|
|
let instances = await Self.rawSql(query, [finalState.id]);
|
|
|
|
|
|
|
|
if (instances.length !== 1 || instances[0].workerFk == userId || instances[0].amount > 0)
|
|
|
|
return;
|
|
|
|
|
|
|
|
query = `SELECT COUNT(distinct r.id) > 0 as hasManagerRole
|
|
|
|
FROM clientCredit cc
|
|
|
|
JOIN worker em ON em.id = cc.workerFk
|
|
|
|
JOIN account.user ac ON ac.id = em.userFk
|
|
|
|
JOIN salix.RoleMapping rm ON rm.principalId = ac.id
|
|
|
|
JOIN account.role r on r.id = rm.roleId
|
|
|
|
WHERE rm.principalType = 'USER'
|
|
|
|
AND cc.workerFk = ?
|
|
|
|
AND r.name = 'manager'`;
|
|
|
|
|
|
|
|
let instance = await Self.rawSql(query, [instances[0].workerFk]);
|
|
|
|
|
|
|
|
if (instance[0].hasManagerRole > 0)
|
|
|
|
throw new Error('Only manager can change the credit');
|
|
|
|
}
|
|
|
|
};
|