module.exports = Self => { Self.clone = async(sales, servicesIds, withWarehouse, group, negative, options) => { const models = Self.app.models; const myOptions = {}; let tx; if (typeof options == 'object') Object.assign(myOptions, options); if (!myOptions.transaction) { tx = await Self.beginTransaction({}); myOptions.transaction = tx; } const ticketsIds = [...new Set(sales.map(sale => sale.ticketFk))]; const now = Date.vnNew(); let updatedTickets = []; let newTicket; const filter = { include: [ {relation: 'address'}, { relation: 'sale', where: {saleFk: {inq: sales}}, }, ] }; try { for (const [index, ticketId] of ticketsIds.entries()) { const ticket = await models.Ticket.findById(ticketId, filter, myOptions); if (!group || !index) { newTicket = await models.Ticket.create({ clientFk: ticket.clientFk, shipped: now, addressFk: ticket.address().id, nickname: ticket.address().nickname, warehouseFk: withWarehouse ? ticket.warehouseFk : null, companyFk: ticket.companyFk, landed: now, }, myOptions); updatedTickets.push(newTicket); } const salesByTicket = ticket.sale(); const saleIds = salesByTicket.map(sale => sale.id); const saleComponentsFilter = { where: {saleFk: {inq: saleIds}}, scope: { fields: ['saleFk', 'componentFk', 'value'] } }; for (const sale of salesByTicket) { const createdSale = await models.Sale.create({ ticketFk: newTicket.id, itemFk: sale.itemFk, quantity: (negative) ? - sale.quantity : sale.quantity, concept: sale.concept, price: sale.price, discount: sale.discount, }, myOptions); const components = await models.SaleComponent.find(saleComponentsFilter, myOptions); // Revisar con Alex // const components = sale.components(); for (const component of components) component.saleFk = createdSale.id; await models.SaleComponent.create(components, myOptions); } } if (servicesIds && servicesIds.length > 0) { const servicesFilter = { where: {id: {inq: servicesIds}} }; const services = await models.TicketService.find(servicesFilter, myOptions); for (const service of services) { await models.TicketService.create({ description: service.description, quantity: (negative) ? - service.quantity : service.quantity, price: service.price, taxClassFk: service.taxClassFk, ticketFk: service.ticketFk, ticketServiceTypeFk: service.ticketServiceTypeFk, }, myOptions); } } const query = `CALL vn.ticket_recalc(?, NULL)`; if (group) { await Self.rawSql(query, [newTicket.id], myOptions); if (tx) await tx.commit(); return newTicket; } else { for (const updatedTicket of updatedTickets) await Self.rawSql(query, [updatedTicket.id], myOptions); if (tx) await tx.commit(); return /* updatedTickets */updatedTickets; } } catch (e) { if (tx) await tx.rollback(); throw e; } }; };