Merge pull request 'test' (!1873) from test into master
gitea/salix/pipeline/head This commit looks good
Details
gitea/salix/pipeline/head This commit looks good
Details
Reviewed-on: #1873 Reviewed-by: Alex Moreno <alexm@verdnatura.es>
This commit is contained in:
commit
758b468c68
|
@ -49,13 +49,7 @@ module.exports = Self => {
|
||||||
if (vnUser.twoFactor)
|
if (vnUser.twoFactor)
|
||||||
throw new ForbiddenError(null, 'REQUIRES_2FA');
|
throw new ForbiddenError(null, 'REQUIRES_2FA');
|
||||||
}
|
}
|
||||||
const validateLogin = await Self.validateLogin(user, password);
|
return Self.validateLogin(user, password, ctx);
|
||||||
await Self.app.models.SignInLog.create({
|
|
||||||
token: validateLogin.token,
|
|
||||||
userFk: vnUser.id,
|
|
||||||
ip: ctx.req.ip
|
|
||||||
});
|
|
||||||
return validateLogin;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
Self.passExpired = async vnUser => {
|
Self.passExpired = async vnUser => {
|
||||||
|
|
|
@ -2,7 +2,7 @@ const {models} = require('vn-loopback/server/server');
|
||||||
|
|
||||||
describe('VnUser Sign-in()', () => {
|
describe('VnUser Sign-in()', () => {
|
||||||
const employeeId = 1;
|
const employeeId = 1;
|
||||||
const unauthCtx = {
|
const unAuthCtx = {
|
||||||
req: {
|
req: {
|
||||||
headers: {},
|
headers: {},
|
||||||
connection: {
|
connection: {
|
||||||
|
@ -15,20 +15,21 @@ describe('VnUser Sign-in()', () => {
|
||||||
const {VnUser, AccessToken, SignInLog} = models;
|
const {VnUser, AccessToken, SignInLog} = models;
|
||||||
describe('when credentials are correct', () => {
|
describe('when credentials are correct', () => {
|
||||||
it('should return the token if user uses email', async() => {
|
it('should return the token if user uses email', async() => {
|
||||||
let login = await VnUser.signIn(unauthCtx, 'salesAssistant@mydomain.com', 'nightmare');
|
let login = await VnUser.signIn(unAuthCtx, 'salesAssistant@mydomain.com', 'nightmare');
|
||||||
let accessToken = await AccessToken.findById(login.token);
|
let accessToken = await AccessToken.findById(login.token);
|
||||||
let ctx = {req: {accessToken: accessToken}};
|
let ctx = {req: {accessToken: accessToken}};
|
||||||
let signInLog = await SignInLog.find({where: {token: accessToken.id}});
|
let signInLog = await SignInLog.find({where: {token: accessToken.id}});
|
||||||
|
|
||||||
expect(signInLog.length).toEqual(1);
|
expect(signInLog.length).toEqual(1);
|
||||||
expect(signInLog[0].userFk).toEqual(accessToken.userId);
|
expect(signInLog[0].userFk).toEqual(accessToken.userId);
|
||||||
|
expect(signInLog[0].owner).toEqual(true);
|
||||||
expect(login.token).toBeDefined();
|
expect(login.token).toBeDefined();
|
||||||
|
|
||||||
await VnUser.logout(ctx.req.accessToken.id);
|
await VnUser.logout(ctx.req.accessToken.id);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return the token', async() => {
|
it('should return the token', async() => {
|
||||||
let login = await VnUser.signIn(unauthCtx, 'salesAssistant', 'nightmare');
|
let login = await VnUser.signIn(unAuthCtx, 'salesAssistant', 'nightmare');
|
||||||
let accessToken = await AccessToken.findById(login.token);
|
let accessToken = await AccessToken.findById(login.token);
|
||||||
let ctx = {req: {accessToken: accessToken}};
|
let ctx = {req: {accessToken: accessToken}};
|
||||||
|
|
||||||
|
@ -38,7 +39,7 @@ describe('VnUser Sign-in()', () => {
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return the token if the user doesnt exist but the client does', async() => {
|
it('should return the token if the user doesnt exist but the client does', async() => {
|
||||||
let login = await VnUser.signIn(unauthCtx, 'PetterParker', 'nightmare');
|
let login = await VnUser.signIn(unAuthCtx, 'PetterParker', 'nightmare');
|
||||||
let accessToken = await AccessToken.findById(login.token);
|
let accessToken = await AccessToken.findById(login.token);
|
||||||
let ctx = {req: {accessToken: accessToken}};
|
let ctx = {req: {accessToken: accessToken}};
|
||||||
|
|
||||||
|
@ -53,7 +54,7 @@ describe('VnUser Sign-in()', () => {
|
||||||
let error;
|
let error;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await VnUser.signIn(unauthCtx, 'IDontExist', 'TotallyWrongPassword');
|
await VnUser.signIn(unAuthCtx, 'IDontExist', 'TotallyWrongPassword');
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
error = e;
|
error = e;
|
||||||
}
|
}
|
||||||
|
@ -74,7 +75,7 @@ describe('VnUser Sign-in()', () => {
|
||||||
const options = {transaction: tx};
|
const options = {transaction: tx};
|
||||||
await employee.updateAttribute('twoFactor', 'email', options);
|
await employee.updateAttribute('twoFactor', 'email', options);
|
||||||
|
|
||||||
await VnUser.signIn(unauthCtx, 'employee', 'nightmare', options);
|
await VnUser.signIn(unAuthCtx, 'employee', 'nightmare', options);
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
|
@ -99,7 +100,7 @@ describe('VnUser Sign-in()', () => {
|
||||||
const options = {transaction: tx};
|
const options = {transaction: tx};
|
||||||
await employee.updateAttribute('passExpired', yesterday, options);
|
await employee.updateAttribute('passExpired', yesterday, options);
|
||||||
|
|
||||||
await VnUser.signIn(unauthCtx, 'employee', 'nightmare', options);
|
await VnUser.signIn(unAuthCtx, 'employee', 'nightmare', options);
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
|
|
|
@ -124,20 +124,42 @@ module.exports = function(Self) {
|
||||||
|
|
||||||
return email.send();
|
return email.send();
|
||||||
});
|
});
|
||||||
Self.signInValidate = (user, userToken) => {
|
|
||||||
|
/**
|
||||||
|
* Sign-in validate
|
||||||
|
* @param {String} user The user
|
||||||
|
* @param {Object} userToken Options
|
||||||
|
* @param {Object} token accessToken
|
||||||
|
* @param {Object} ctx context
|
||||||
|
*/
|
||||||
|
Self.signInValidate = async(user, userToken, token, ctx) => {
|
||||||
const [[key, value]] = Object.entries(Self.userUses(user));
|
const [[key, value]] = Object.entries(Self.userUses(user));
|
||||||
if (userToken[key].toLowerCase().trim() !== value.toLowerCase().trim()) {
|
const isOwner = Self.rawSql(`SELECT ? = ? `, [userToken[key], value]);
|
||||||
console.error('ERROR!!! - Signin with other user', userToken, user);
|
await Self.app.models.SignInLog.create({
|
||||||
|
userName: user,
|
||||||
|
token: token.id,
|
||||||
|
userFk: userToken.id,
|
||||||
|
ip: ctx.req.ip,
|
||||||
|
owner: isOwner
|
||||||
|
});
|
||||||
|
if (!isOwner)
|
||||||
throw new UserError('Try again');
|
throw new UserError('Try again');
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
Self.validateLogin = async function(user, password) {
|
/**
|
||||||
|
* Validate login params
|
||||||
|
* @param {String} user The user
|
||||||
|
* @param {String} password
|
||||||
|
* @param {Object} ctx context
|
||||||
|
*/
|
||||||
|
Self.validateLogin = async function(user, password, ctx) {
|
||||||
const loginInfo = Object.assign({password}, Self.userUses(user));
|
const loginInfo = Object.assign({password}, Self.userUses(user));
|
||||||
const token = await Self.login(loginInfo, 'user');
|
const token = await Self.login(loginInfo, 'user');
|
||||||
|
|
||||||
const userToken = await token.user.get();
|
const userToken = await token.user.get();
|
||||||
Self.signInValidate(user, userToken);
|
|
||||||
|
if (ctx)
|
||||||
|
await Self.signInValidate(user, userToken, token, ctx);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await Self.app.models.Account.sync(userToken.name, password);
|
await Self.app.models.Account.sync(userToken.name, password);
|
||||||
|
@ -187,8 +209,8 @@ module.exports = function(Self) {
|
||||||
};
|
};
|
||||||
|
|
||||||
Self.sharedClass._methods.find(method => method.name == 'changePassword').ctor.settings.acls =
|
Self.sharedClass._methods.find(method => method.name == 'changePassword').ctor.settings.acls =
|
||||||
Self.sharedClass._methods.find(method => method.name == 'changePassword').ctor.settings.acls
|
Self.sharedClass._methods.find(method => method.name == 'changePassword').ctor.settings.acls
|
||||||
.filter(acl => acl.property != 'changePassword');
|
.filter(acl => acl.property != 'changePassword');
|
||||||
|
|
||||||
Self.userSecurity = async(ctx, userId, options) => {
|
Self.userSecurity = async(ctx, userId, options) => {
|
||||||
const models = Self.app.models;
|
const models = Self.app.models;
|
||||||
|
@ -226,10 +248,12 @@ module.exports = function(Self) {
|
||||||
|
|
||||||
const env = process.env.NODE_ENV;
|
const env = process.env.NODE_ENV;
|
||||||
const liliumUrl = await Self.app.models.Url.findOne({
|
const liliumUrl = await Self.app.models.Url.findOne({
|
||||||
where: {and: [
|
where: {
|
||||||
{appName: 'lilium'},
|
and: [
|
||||||
{environment: env}
|
{appName: 'lilium'},
|
||||||
]}
|
{environment: env}
|
||||||
|
]
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
class Mailer {
|
class Mailer {
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
|
|
||||||
|
|
||||||
--
|
--
|
||||||
-- Table structure for table `signInLog`
|
-- Table structure for table `signInLog`
|
||||||
-- Description: log to debug cross-login error
|
-- Description: log to debug cross-login error
|
||||||
|
@ -13,7 +12,9 @@ CREATE TABLE `account`.`signInLog` (
|
||||||
`token` varchar(255) NOT NULL ,
|
`token` varchar(255) NOT NULL ,
|
||||||
`userFk` int(10) unsigned DEFAULT NULL,
|
`userFk` int(10) unsigned DEFAULT NULL,
|
||||||
`creationDate` timestamp NULL DEFAULT current_timestamp(),
|
`creationDate` timestamp NULL DEFAULT current_timestamp(),
|
||||||
|
`userName` varchar(30) NOT NULL,
|
||||||
`ip` varchar(100) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL,
|
`ip` varchar(100) CHARACTER SET utf8mb3 COLLATE utf8mb3_general_ci NOT NULL,
|
||||||
|
`owner` tinyint(1) DEFAULT 1,
|
||||||
KEY `userFk` (`userFk`),
|
KEY `userFk` (`userFk`),
|
||||||
CONSTRAINT `signInLog_ibfk_1` FOREIGN KEY (`userFk`) REFERENCES `user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
|
CONSTRAINT `signInLog_ibfk_1` FOREIGN KEY (`userFk`) REFERENCES `user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
|
||||||
);
|
);
|
|
@ -2347,9 +2347,11 @@ INSERT INTO `vn`.`zoneEvent`(`zoneFk`, `type`, `weekDays`)
|
||||||
(8, 'indefinitely', 'mon,tue,wed,thu,fri,sat,sun'),
|
(8, 'indefinitely', 'mon,tue,wed,thu,fri,sat,sun'),
|
||||||
(10, 'indefinitely', 'mon,tue,wed,thu,fri,sat,sun');
|
(10, 'indefinitely', 'mon,tue,wed,thu,fri,sat,sun');
|
||||||
|
|
||||||
INSERT INTO `vn`.`zoneEvent`(`zoneFk`, `type`, `started`, `ended`)
|
INSERT INTO `vn`.`zoneEvent`(`zoneFk`, `type`, `started`, `ended`, `weekDays`)
|
||||||
VALUES
|
VALUES
|
||||||
(9, 'range', DATE_ADD(util.VN_CURDATE(), INTERVAL -1 YEAR), DATE_ADD(util.VN_CURDATE(), INTERVAL +1 YEAR));
|
(9, 'range', DATE_ADD(util.VN_CURDATE(), INTERVAL -1 YEAR), DATE_ADD(util.VN_CURDATE(), INTERVAL +1 YEAR), 'mon'),
|
||||||
|
(9, 'range', util.VN_CURDATE(), NULL, 'tue'),
|
||||||
|
(9, 'range', NULL, util.VN_CURDATE(), 'wed');
|
||||||
|
|
||||||
INSERT INTO `vn`.`workerTimeControl`(`userFk`, `timed`, `manual`, `direction`, `isSendMail`)
|
INSERT INTO `vn`.`workerTimeControl`(`userFk`, `timed`, `manual`, `direction`, `isSendMail`)
|
||||||
VALUES
|
VALUES
|
||||||
|
|
|
@ -25,7 +25,15 @@
|
||||||
"type": "number"
|
"type": "number"
|
||||||
},
|
},
|
||||||
"ip": {
|
"ip": {
|
||||||
"type": "string"
|
"type": "string"
|
||||||
|
},
|
||||||
|
"userName": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"owner": {
|
||||||
|
"type": "boolean",
|
||||||
|
"required": true,
|
||||||
|
"default": true
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"relations": {
|
"relations": {
|
||||||
|
|
|
@ -3,99 +3,101 @@ const buildFilter = require('vn-loopback/util/filter').buildFilter;
|
||||||
const mergeFilters = require('vn-loopback/util/filter').mergeFilters;
|
const mergeFilters = require('vn-loopback/util/filter').mergeFilters;
|
||||||
|
|
||||||
module.exports = Self => {
|
module.exports = Self => {
|
||||||
Self.remoteMethod('getExternalCmrs', {
|
Self.remoteMethod('getExternalCmrs', {
|
||||||
description: 'Returns an array of external cmrs',
|
description: 'Returns an array of external cmrs',
|
||||||
accessType: 'READ',
|
accessType: 'READ',
|
||||||
accepts: [
|
accepts: [
|
||||||
{
|
{
|
||||||
arg: 'filter',
|
arg: 'filter',
|
||||||
type: 'object',
|
type: 'object',
|
||||||
description: 'Filter defining where, order, offset, and limit - must be a JSON-encoded string',
|
description: 'Filter defining where, order, offset, and limit - must be a JSON-encoded string',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'cmrFk',
|
arg: 'cmrFk',
|
||||||
type: 'integer',
|
type: 'integer',
|
||||||
description: 'Searchs the route by id',
|
description: 'Searchs the route by id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'ticketFk',
|
arg: 'ticketFk',
|
||||||
type: 'integer',
|
type: 'integer',
|
||||||
description: 'The worker id',
|
description: 'The worker id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'routeFk',
|
arg: 'routeFk',
|
||||||
type: 'integer',
|
type: 'integer',
|
||||||
description: 'The route id',
|
description: 'The route id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'country',
|
arg: 'country',
|
||||||
type: 'string',
|
type: 'string',
|
||||||
description: 'The agencyMode id',
|
description: 'The agencyMode id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'clientFk',
|
arg: 'clientFk',
|
||||||
type: 'integer',
|
type: 'integer',
|
||||||
description: 'The vehicle id',
|
description: 'The vehicle id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'hasCmrDms',
|
arg: 'hasCmrDms',
|
||||||
type: 'boolean',
|
type: 'boolean',
|
||||||
description: 'The vehicle id',
|
description: 'The vehicle id',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
arg: 'shipped',
|
arg: 'shipped',
|
||||||
type: 'date',
|
type: 'date',
|
||||||
description: 'The to date filter',
|
description: 'The to date filter',
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
returns: {
|
returns: {
|
||||||
type: ['object'],
|
type: ['object'],
|
||||||
root: true
|
root: true
|
||||||
},
|
},
|
||||||
http: {
|
http: {
|
||||||
path: `/getExternalCmrs`,
|
path: `/getExternalCmrs`,
|
||||||
verb: 'GET'
|
verb: 'GET'
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Self.getExternalCmrs = async(
|
Self.getExternalCmrs = async(
|
||||||
filter,
|
filter,
|
||||||
cmrFk,
|
cmrFk,
|
||||||
ticketFk,
|
ticketFk,
|
||||||
routeFk,
|
routeFk,
|
||||||
country,
|
country,
|
||||||
clientFk,
|
clientFk,
|
||||||
hasCmrDms,
|
hasCmrDms,
|
||||||
shipped,
|
shipped,
|
||||||
options
|
options
|
||||||
) => {
|
) => {
|
||||||
const params = {
|
const params = {
|
||||||
cmrFk,
|
cmrFk,
|
||||||
ticketFk,
|
ticketFk,
|
||||||
routeFk,
|
routeFk,
|
||||||
country,
|
country,
|
||||||
clientFk,
|
clientFk,
|
||||||
hasCmrDms,
|
hasCmrDms,
|
||||||
shipped,
|
shipped,
|
||||||
};
|
};
|
||||||
const conn = Self.dataSource.connector;
|
const conn = Self.dataSource.connector;
|
||||||
|
|
||||||
let where = buildFilter(params, (param, value) => {return {[param]: value}});
|
let where = buildFilter(params, (param, value) => {
|
||||||
filter = mergeFilters(filter, {where});
|
return {[param]: value};
|
||||||
|
});
|
||||||
|
filter = mergeFilters(filter, {where});
|
||||||
|
|
||||||
if (!filter.where) {
|
if (!filter.where) {
|
||||||
const yesterday = new Date();
|
const yesterday = new Date();
|
||||||
yesterday.setDate(yesterday.getDate() - 1);
|
yesterday.setDate(yesterday.getDate() - 1);
|
||||||
filter.where = {'shipped': yesterday.toISOString().split('T')[0]}
|
filter.where = {'shipped': yesterday.toISOString().split('T')[0]};
|
||||||
}
|
}
|
||||||
|
|
||||||
const myOptions = {};
|
const myOptions = {};
|
||||||
|
|
||||||
if (typeof options == 'object')
|
if (typeof options == 'object')
|
||||||
Object.assign(myOptions, options);
|
Object.assign(myOptions, options);
|
||||||
|
|
||||||
let stmts = [];
|
let stmts = [];
|
||||||
const stmt = new ParameterizedSQL(`
|
const stmt = new ParameterizedSQL(`
|
||||||
SELECT *
|
SELECT *
|
||||||
FROM (
|
FROM (
|
||||||
SELECT t.cmrFk,
|
SELECT t.cmrFk,
|
||||||
|
@ -129,13 +131,13 @@ module.exports = Self => {
|
||||||
AND dm.code = 'DELIVERY'
|
AND dm.code = 'DELIVERY'
|
||||||
AND t.cmrFk
|
AND t.cmrFk
|
||||||
) sub
|
) sub
|
||||||
`);
|
`);
|
||||||
|
|
||||||
stmt.merge(conn.makeSuffix(filter));
|
stmt.merge(conn.makeSuffix(filter));
|
||||||
const itemsIndex = stmts.push(stmt) - 1;
|
const itemsIndex = stmts.push(stmt) - 1;
|
||||||
|
|
||||||
const sql = ParameterizedSQL.join(stmts, ';');
|
const sql = ParameterizedSQL.join(stmts, ';');
|
||||||
const result = await conn.executeStmt(sql);
|
const result = await conn.executeStmt(sql);
|
||||||
return itemsIndex === 0 ? result : result[itemsIndex];
|
return itemsIndex === 0 ? result : result[itemsIndex];
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
|
@ -35,44 +35,39 @@ module.exports = Self => {
|
||||||
if (typeof options == 'object')
|
if (typeof options == 'object')
|
||||||
Object.assign(myOptions, options);
|
Object.assign(myOptions, options);
|
||||||
|
|
||||||
query = `
|
ended = simpleDate(ended);
|
||||||
SELECT *
|
started = simpleDate(started);
|
||||||
FROM vn.zoneEvent
|
|
||||||
WHERE zoneFk = ?
|
|
||||||
AND ((type = 'indefinitely')
|
|
||||||
OR (type = 'day' AND dated BETWEEN ? AND ?)
|
|
||||||
OR (type = 'range'
|
|
||||||
AND (
|
|
||||||
(started BETWEEN ? AND ?)
|
|
||||||
OR
|
|
||||||
(ended BETWEEN ? AND ?)
|
|
||||||
OR
|
|
||||||
(started <= ? AND ended >= ?)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
ORDER BY type='indefinitely' DESC, type='range' DESC, type='day' DESC;`;
|
|
||||||
const events = await Self.rawSql(query,
|
|
||||||
[zoneFk, started, ended, started, ended, started, ended, started, ended], myOptions);
|
|
||||||
|
|
||||||
query = `
|
query = `
|
||||||
SELECT e.*
|
SELECT *
|
||||||
FROM vn.zoneExclusion e
|
FROM vn.zoneEvent
|
||||||
LEFT JOIN vn.zoneExclusionGeo eg ON eg.zoneExclusionFk = e.id
|
WHERE zoneFk = ?
|
||||||
WHERE e.zoneFk = ?
|
AND (IFNULL(started, ?) <= ? AND IFNULL(ended,?) >= ?)
|
||||||
AND e.dated BETWEEN ? AND ?
|
ORDER BY type='indefinitely' DESC, type='range' DESC, type='day' DESC;`;
|
||||||
AND eg.zoneExclusionFk IS NULL;`;
|
const events = await Self.rawSql(query,
|
||||||
|
[zoneFk, started, ended, ended, started], myOptions);
|
||||||
|
|
||||||
|
query = `
|
||||||
|
SELECT e.*
|
||||||
|
FROM vn.zoneExclusion e
|
||||||
|
LEFT JOIN vn.zoneExclusionGeo eg ON eg.zoneExclusionFk = e.id
|
||||||
|
WHERE e.zoneFk = ?
|
||||||
|
AND e.dated BETWEEN ? AND ?
|
||||||
|
AND eg.zoneExclusionFk IS NULL;`;
|
||||||
const exclusions = await Self.rawSql(query, [zoneFk, started, ended], myOptions);
|
const exclusions = await Self.rawSql(query, [zoneFk, started, ended], myOptions);
|
||||||
|
|
||||||
query = `
|
query = `
|
||||||
SELECT eg.*, e.zoneFk, e.dated, e.created, e.userFk
|
SELECT eg.*, e.zoneFk, e.dated, e.created, e.userFk
|
||||||
FROM vn.zoneExclusion e
|
FROM vn.zoneExclusion e
|
||||||
LEFT JOIN vn.zoneExclusionGeo eg ON eg.zoneExclusionFk = e.id
|
LEFT JOIN vn.zoneExclusionGeo eg ON eg.zoneExclusionFk = e.id
|
||||||
WHERE e.zoneFk = ?
|
WHERE e.zoneFk = ?
|
||||||
AND e.dated BETWEEN ? AND ?
|
AND e.dated BETWEEN ? AND ?
|
||||||
AND eg.zoneExclusionFk IS NOT NULL;`;
|
AND eg.zoneExclusionFk IS NOT NULL;`;
|
||||||
const geoExclusions = await Self.rawSql(query, [zoneFk, started, ended], myOptions);
|
const geoExclusions = await Self.rawSql(query, [zoneFk, started, ended], myOptions);
|
||||||
|
|
||||||
return {events, exclusions, geoExclusions};
|
return {events, exclusions, geoExclusions};
|
||||||
};
|
};
|
||||||
|
function simpleDate(date) {
|
||||||
|
return date.toISOString().split('T')[0];
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -30,7 +30,7 @@ describe('zone getEventsFiltered()', () => {
|
||||||
|
|
||||||
const result = await models.Zone.getEventsFiltered(9, today, today, options);
|
const result = await models.Zone.getEventsFiltered(9, today, today, options);
|
||||||
|
|
||||||
expect(result.events.length).toEqual(1);
|
expect(result.events.length).toEqual(3);
|
||||||
expect(result.exclusions.length).toEqual(0);
|
expect(result.exclusions.length).toEqual(0);
|
||||||
|
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
|
@ -47,11 +47,12 @@ describe('zone getEventsFiltered()', () => {
|
||||||
const options = {transaction: tx};
|
const options = {transaction: tx};
|
||||||
const date = Date.vnNew();
|
const date = Date.vnNew();
|
||||||
date.setFullYear(date.getFullYear() - 2);
|
date.setFullYear(date.getFullYear() - 2);
|
||||||
const dateTomorrow = new Date(date.setDate(date.getDate() + 1));
|
const dateTomorrow = new Date(date);
|
||||||
|
dateTomorrow.setDate(dateTomorrow.getDate() + 1);
|
||||||
|
|
||||||
const result = await models.Zone.getEventsFiltered(9, date, dateTomorrow, options);
|
const result = await models.Zone.getEventsFiltered(9, date, dateTomorrow, options);
|
||||||
|
|
||||||
expect(result.events.length).toEqual(0);
|
expect(result.events.length).toEqual(1);
|
||||||
expect(result.exclusions.length).toEqual(0);
|
expect(result.exclusions.length).toEqual(0);
|
||||||
|
|
||||||
await tx.rollback();
|
await tx.rollback();
|
||||||
|
|
Loading…
Reference in New Issue