2019-03-22 07:28:57 +00:00
|
|
|
const UserError = require('vn-loopback/util/user-error');
|
|
|
|
|
|
|
|
module.exports = Self => {
|
|
|
|
Self.remoteMethodCtx('absences', {
|
|
|
|
description: 'Returns an array of absences from an specified worker',
|
|
|
|
accepts: [{
|
|
|
|
arg: 'workerFk',
|
|
|
|
type: 'Number',
|
|
|
|
required: true,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
arg: 'started',
|
|
|
|
type: 'Date',
|
|
|
|
required: true,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
arg: 'ended',
|
|
|
|
type: 'Date',
|
|
|
|
required: true,
|
|
|
|
}],
|
|
|
|
returns: [{
|
|
|
|
arg: 'calendar'
|
|
|
|
},
|
|
|
|
{
|
2019-04-23 11:29:52 +00:00
|
|
|
arg: 'absences',
|
|
|
|
type: 'Number'
|
2019-03-22 07:28:57 +00:00
|
|
|
},
|
|
|
|
{
|
2019-04-23 11:29:52 +00:00
|
|
|
arg: 'holidays',
|
|
|
|
type: 'Number'
|
2019-03-22 07:28:57 +00:00
|
|
|
}],
|
|
|
|
http: {
|
|
|
|
path: `/absences`,
|
|
|
|
verb: 'GET'
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
Self.absences = async(ctx, workerFk, started, ended) => {
|
|
|
|
const models = Self.app.models;
|
|
|
|
const conn = Self.dataSource.connector;
|
|
|
|
const myUserId = ctx.req.accessToken.userId;
|
|
|
|
const myWorker = await models.Worker.findOne({where: {userFk: myUserId}});
|
|
|
|
const calendar = {totalHolidays: 0, holidaysEnjoyed: 0};
|
|
|
|
const holidays = [];
|
|
|
|
const stmts = [];
|
|
|
|
|
|
|
|
// Get subordinates
|
|
|
|
stmts.push(new ParameterizedSQL('CALL vn.subordinateGetList(?)', [myWorker.id]));
|
|
|
|
let subordinatesIndex = stmts.push('SELECT * FROM tmp.subordinate') - 1;
|
|
|
|
let sql = ParameterizedSQL.join(stmts, ';');
|
|
|
|
let result = await conn.executeStmt(sql);
|
|
|
|
|
|
|
|
const subordinates = result[subordinatesIndex];
|
|
|
|
const isSubordinate = subordinates.find(subordinate => {
|
|
|
|
return subordinate.workerFk === workerFk;
|
|
|
|
});
|
|
|
|
const isHr = await models.Account.hasRole(myUserId, 'hr');
|
|
|
|
|
|
|
|
if (!isHr && workerFk !== myWorker.id && !isSubordinate)
|
|
|
|
throw new UserError(`You don't have enough privileges`);
|
|
|
|
|
|
|
|
|
|
|
|
// Get absences of year
|
|
|
|
let absences = await Self.find({
|
|
|
|
include: {
|
|
|
|
relation: 'absenceType'
|
|
|
|
},
|
|
|
|
where: {
|
|
|
|
workerFk: workerFk,
|
|
|
|
dated: {between: [started, ended]}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
absences.forEach(absence => {
|
|
|
|
if (absence.absenceType().id === 1)
|
|
|
|
calendar.holidaysEnjoyed++;
|
|
|
|
|
|
|
|
absence.dated = new Date(absence.dated);
|
|
|
|
absence.dated.setHours(0, 0, 0, 0);
|
|
|
|
});
|
|
|
|
|
|
|
|
// Get active contracts on current year
|
|
|
|
const year = started.getFullYear();
|
|
|
|
const contracts = await models.WorkerLabour.find({
|
|
|
|
include: [{
|
|
|
|
relation: 'holidays',
|
|
|
|
scope: {
|
|
|
|
where: {year}
|
|
|
|
}
|
|
|
|
},
|
|
|
|
{
|
|
|
|
relation: 'workCenter',
|
|
|
|
scope: {
|
|
|
|
include: {
|
|
|
|
relation: 'holidays',
|
|
|
|
scope: {
|
|
|
|
include: [{
|
|
|
|
relation: 'detail'
|
|
|
|
},
|
|
|
|
{
|
|
|
|
relation: 'type'
|
|
|
|
}],
|
|
|
|
where: {
|
|
|
|
dated: {between: [started, ended]}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}],
|
|
|
|
where: {
|
|
|
|
and: [
|
|
|
|
{workerFk: workerFk},
|
|
|
|
{or: [{
|
|
|
|
ended: {gte: [started]}
|
|
|
|
}, {ended: null}]}
|
|
|
|
],
|
|
|
|
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
// Get number of total holidays
|
|
|
|
contracts.forEach(contract => {
|
|
|
|
let totalHolidays = contract.holidays().days;
|
|
|
|
|
|
|
|
if (contract.started && contract.ended)
|
2019-04-03 09:36:10 +00:00
|
|
|
totalHolidays = getHolidaysByContract(started, contract);
|
2019-03-22 07:28:57 +00:00
|
|
|
|
|
|
|
calendar.totalHolidays += totalHolidays;
|
|
|
|
|
|
|
|
|
|
|
|
let holidayList = contract.workCenter().holidays();
|
|
|
|
for (let day of holidayList) {
|
|
|
|
day.dated = new Date(day.dated);
|
|
|
|
day.dated.setHours(0, 0, 0, 0);
|
|
|
|
|
|
|
|
holidays.push(day);
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
return [calendar, absences, holidays];
|
|
|
|
};
|
|
|
|
|
2019-04-03 09:36:10 +00:00
|
|
|
function getHolidaysByContract(started, contract) {
|
2019-03-22 07:28:57 +00:00
|
|
|
const dayTimestamp = 1000 * 60 * 60 * 24;
|
|
|
|
const endedTime = contract.ended.getTime();
|
2019-04-03 09:36:10 +00:00
|
|
|
const startedTime = started.getTime();
|
2019-03-22 07:28:57 +00:00
|
|
|
const contractDays = Math.floor((endedTime - startedTime) / dayTimestamp);
|
|
|
|
|
2019-04-23 11:29:52 +00:00
|
|
|
if (contractDays < 365) {
|
|
|
|
let holidays = contract.holidays().days * (contractDays + 1) / 365;
|
|
|
|
let integerPart = parseInt(holidays);
|
|
|
|
let decimalPart = holidays - integerPart;
|
|
|
|
let decimal = decimalPart >= 0.5 ? 0.5 : 0;
|
|
|
|
|
|
|
|
holidays = integerPart + decimal;
|
|
|
|
|
|
|
|
return holidays;
|
|
|
|
}
|
2019-03-22 07:28:57 +00:00
|
|
|
|
|
|
|
return contract.holidays().days;
|
|
|
|
}
|
|
|
|
};
|