refactor(order): catalogFilter, confirm and filter transactions

This commit is contained in:
Carlos Jimenez Ruiz 2021-10-25 13:13:05 +02:00
parent b055618577
commit f62814e81e
4 changed files with 136 additions and 81 deletions

View File

@ -7,28 +7,28 @@ module.exports = Self => {
accepts: [ accepts: [
{ {
arg: 'orderFk', arg: 'orderFk',
type: 'Number', type: 'number',
required: true required: true
}, },
{ {
arg: 'orderBy', arg: 'orderBy',
type: 'Object', type: 'object',
description: 'Items order', description: 'Items order',
required: true required: true
}, },
{ {
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: 'tagGroups', arg: 'tagGroups',
type: ['Object'], type: ['object'],
description: 'Filter by tag' description: 'Filter by tag'
}, },
], ],
returns: { returns: {
type: ['Object'], type: ['object'],
root: true, root: true,
}, },
http: { http: {
@ -37,8 +37,13 @@ module.exports = Self => {
}, },
}); });
Self.catalogFilter = async(orderFk, orderBy, filter, tagGroups) => { Self.catalogFilter = async(orderFk, orderBy, filter, tagGroups, options) => {
let conn = Self.dataSource.connector; const conn = Self.dataSource.connector;
const myOptions = {};
if (typeof options == 'object')
Object.assign(myOptions, options);
const stmts = []; const stmts = [];
let stmt; let stmt;
@ -85,7 +90,7 @@ module.exports = Self => {
stmts.push(stmt); stmts.push(stmt);
// Calculate items // Calculate items
const order = await Self.findById(orderFk); const order = await Self.findById(orderFk, null, myOptions);
stmts.push(new ParameterizedSQL( stmts.push(new ParameterizedSQL(
'CALL vn.catalog_calculate(?, ?, ?)', [ 'CALL vn.catalog_calculate(?, ?, ?)', [
order.landed, order.landed,
@ -131,9 +136,9 @@ module.exports = Self => {
params: [orderBy.field], params: [orderBy.field],
}); });
let way = orderBy.way == 'DESC' ? 'DESC' : 'ASC'; const way = orderBy.way == 'DESC' ? 'DESC' : 'ASC';
let tag = await Self.app.models.Tag.findById(orderBy.field); const tag = await Self.app.models.Tag.findById(orderBy.field, null, myOptions);
let orderSql = ` const orderSql = `
ORDER BY ORDER BY
itg.value IS NULL, itg.value IS NULL,
${tag.isQuantitative ? 'CAST(itg.value AS SIGNED)' : 'itg.value'} ${tag.isQuantitative ? 'CAST(itg.value AS SIGNED)' : 'itg.value'}
@ -181,7 +186,7 @@ module.exports = Self => {
stmts.push('CALL vn.ticketCalculatePurge()'); stmts.push('CALL vn.ticketCalculatePurge()');
const sql = ParameterizedSQL.join(stmts, ';'); const sql = ParameterizedSQL.join(stmts, ';');
const result = await conn.executeStmt(sql); const result = await conn.executeStmt(sql, myOptions);
// Add prices to items // Add prices to items
result[itemsIndex].forEach(item => { result[itemsIndex].forEach(item => {

View File

@ -19,9 +19,29 @@ module.exports = Self => {
} }
}); });
Self.confirm = async(ctx, orderFk) => { Self.confirm = async(ctx, orderFk, option) => {
const userId = ctx.req.accessToken.userId; const userId = ctx.req.accessToken.userId;
let query = `CALL hedera.order_confirmWithUser(?, ?)`; const myOptions = {};
return await Self.rawSql(query, [orderFk, userId]); let tx;
if (typeof options == 'object')
Object.assign(myOptions, options);
if (!myOptions.transaction) {
tx = await Self.beginTransaction({});
myOptions.transaction = tx;
}
try {
const query = `CALL hedera.order_confirmWithUser(?, ?)`;
const response = await Self.rawSql(query, [orderFk, userId], myOptions);
if (tx) await tx.commit();
return response;
} catch (e) {
if (tx) await tx.rollback();
throw e;
}
}; };
}; };

View File

@ -9,60 +9,60 @@ module.exports = Self => {
accepts: [ accepts: [
{ {
arg: 'ctx', arg: 'ctx',
type: 'Object', type: 'object',
http: {source: 'context'} http: {source: 'context'}
}, { }, {
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: 'search', arg: 'search',
type: 'String', type: 'string',
description: `If it's and integer searchs by id, otherwise it searchs by nickname` description: `If it's and integer searchs by id, otherwise it searchs by nickname`
}, { }, {
arg: 'from', arg: 'from',
type: 'Date', type: 'date',
description: `The from date` description: 'The from date'
}, { }, {
arg: 'to', arg: 'to',
type: 'Date', type: 'date',
description: `The to date` description: 'The to date'
}, { }, {
arg: 'id', arg: 'id',
type: 'Integer', type: 'integer',
description: `The ticket id` description: 'The ticket id'
}, { }, {
arg: 'clientFk', arg: 'clientFk',
type: 'Integer', type: 'integer',
description: `The client id` description: 'The client id'
}, { }, {
arg: 'ticketFk', arg: 'ticketFk',
type: 'Integer', type: 'integer',
description: `The ticket id` description: 'The ticket id'
}, { }, {
arg: 'agencyModeFk', arg: 'agencyModeFk',
type: 'Integer', type: 'integer',
description: `The agency mode id` description: 'The agency mode id'
}, { }, {
arg: 'workerFk', arg: 'workerFk',
type: 'Integer', type: 'integer',
description: `The salesperson id` description: 'The salesperson id'
}, { }, {
arg: 'myTeam', arg: 'myTeam',
type: 'Boolean', type: 'boolean',
description: `Whether to show only tickets for the current logged user team (For now it shows only the current user tickets)` description: 'Whether to show only tickets for the current logged user team (currently user tickets)'
}, { }, {
arg: 'isConfirmed', arg: 'isConfirmed',
type: 'Boolean', type: 'boolean',
description: `Order is confirmed` description: 'Order is confirmed'
}, { }, {
arg: 'showEmpty', arg: 'showEmpty',
type: 'boolean', type: 'boolean',
description: `Show empty orders` description: 'Show empty orders'
} }
], ],
returns: { returns: {
type: ['Object'], type: ['object'],
root: true root: true
}, },
http: { http: {
@ -71,14 +71,20 @@ module.exports = Self => {
} }
}); });
Self.filter = async(ctx, filter) => { Self.filter = async(ctx, filter, options) => {
let conn = Self.dataSource.connector; const conn = Self.dataSource.connector;
const myOptions = {};
if (typeof options == 'object')
Object.assign(myOptions, options);
let worker = await Self.app.models.Worker.findOne({ let worker = await Self.app.models.Worker.findOne({
where: {userFk: ctx.req.accessToken.userId}, where: {userFk: ctx.req.accessToken.userId},
include: [ include: [
{relation: 'collegues'} {relation: 'collegues'}
] ]
}); }, myOptions);
const args = ctx.args; const args = ctx.args;
let teamIds = []; let teamIds = [];
@ -92,13 +98,15 @@ module.exports = Self => {
worker = await Self.app.models.Worker.findOne({ worker = await Self.app.models.Worker.findOne({
fields: ['id'], fields: ['id'],
where: {userFk: ctx.req.accessToken.userId} where: {userFk: ctx.req.accessToken.userId}
}); }, myOptions);
teamIds = [worker && worker.id]; teamIds = [worker && worker.id];
} }
if (args && args.myTeam) if (args && args.myTeam)
args.teamIds = teamIds; args.teamIds = teamIds;
let where = buildFilter(args, (param, value) => {
const where = buildFilter(args, (param, value) => {
switch (param) { switch (param) {
case 'search': case 'search':
return /^\d+$/.test(value) return /^\d+$/.test(value)
@ -133,7 +141,7 @@ module.exports = Self => {
}); });
filter = mergeFilters(filter, {where}); filter = mergeFilters(filter, {where});
let stmts = []; const stmts = [];
let stmt; let stmt;
stmt = new ParameterizedSQL( stmt = new ParameterizedSQL(
@ -183,7 +191,7 @@ module.exports = Self => {
stmts.push(`DROP TEMPORARY TABLE tmp.filter`); stmts.push(`DROP TEMPORARY TABLE tmp.filter`);
const sql = ParameterizedSQL.join(stmts, ';'); const sql = ParameterizedSQL.join(stmts, ';');
const result = await conn.executeStmt(sql); const result = await conn.executeStmt(sql, myOptions);
return result[ordersIndex]; return result[ordersIndex];
}; };

View File

@ -1,51 +1,73 @@
const app = require('vn-loopback/server/server'); const models = require('vn-loopback/server/server').models;
describe('order catalogFilter()', () => { describe('order catalogFilter()', () => {
const colorTagId = 1; const colorTagId = 1;
const categoryTagId = 67; const categoryTagId = 67;
it('should return an array of items', async() => { it('should return an array of items', async() => {
let filter = { const tx = await models.Order.beginTransaction({});
where: {
categoryFk: 1,
typeFk: 2
}
};
let tags = [];
let orderFk = 11;
let orderBy = {field: 'relevancy DESC, name', way: 'DESC'};
let result = await app.models.Order.catalogFilter(orderFk, orderBy, filter, tags);
let firstItemId = result[0].id;
expect(result.length).toEqual(4); try {
expect(firstItemId).toEqual(1); const options = {transaction: tx};
const filter = {
where: {
categoryFk: 1,
typeFk: 2
}
};
const tags = [];
const orderFk = 11;
const orderBy = {field: 'relevancy DESC, name', way: 'DESC'};
const result = await models.Order.catalogFilter(orderFk, orderBy, filter, tags, options);
const firstItemId = result[0].id;
expect(result.length).toEqual(4);
expect(firstItemId).toEqual(1);
await tx.rollback();
} catch (e) {
await tx.rollback();
throw e;
}
}); });
it('should now return an array of items based on tag filter', async() => { it('should now return an array of items based on tag filter', async() => {
const filter = { const tx = await models.Order.beginTransaction({});
where: {
categoryFk: 1,
typeFk: 2
}
};
const tagGroups = [ try {
{tagFk: colorTagId, values: [{value: 'Silver'}, {value: 'Brown'}]}, const options = {transaction: tx};
{tagFk: categoryTagId, values: [{value: 'Concussion'}]}
];
const orderFk = 11;
const orderBy = {field: 'relevancy DESC, name', way: 'DESC'};
const result = await app.models.Order.catalogFilter(orderFk, orderBy, filter, tagGroups);
const randomIndex = Math.round(Math.random()); const filter = {
const item = result[randomIndex]; where: {
const itemTags = item.tags; categoryFk: 1,
typeFk: 2
}
};
const colorTag = itemTags.find(tag => tag.tagFk == colorTagId); const tagGroups = [
const categoryTag = itemTags.find(tag => tag.tagFk == categoryTagId); {tagFk: colorTagId, values: [{value: 'Silver'}, {value: 'Brown'}]},
{tagFk: categoryTagId, values: [{value: 'Concussion'}]}
];
const orderFk = 11;
const orderBy = {field: 'relevancy DESC, name', way: 'DESC'};
const result = await models.Order.catalogFilter(orderFk, orderBy, filter, tagGroups, options);
expect(result.length).toEqual(2); const randomIndex = Math.round(Math.random());
expect(colorTag.value).toEqual('Silver'); const item = result[randomIndex];
expect(categoryTag.value).toEqual('Concussion'); const itemTags = item.tags;
const colorTag = itemTags.find(tag => tag.tagFk == colorTagId);
const categoryTag = itemTags.find(tag => tag.tagFk == categoryTagId);
expect(result.length).toEqual(2);
expect(colorTag.value).toEqual('Silver');
expect(categoryTag.value).toEqual('Concussion');
await tx.rollback();
} catch (e) {
await tx.rollback();
throw e;
}
}); });
}); });