const fs = require('fs-extra'); const path = require('path'); const UserError = require('vn-loopback/util/user-error'); module.exports = Self => { Self.remoteMethodCtx('download', { description: 'Download an invoice PDF', accessType: 'READ', accepts: [ { arg: 'id', type: 'string', description: 'The invoice id', http: {source: 'path'} } ], returns: [ { arg: 'body', type: 'file', root: true }, { arg: 'Content-Type', type: 'string', http: {target: 'header'} }, { arg: 'Content-Disposition', type: 'string', http: {target: 'header'} } ], http: { path: '/:id/download', verb: 'GET' } }); Self.download = async function(ctx, id, options) { const models = Self.app.models; const myOptions = {}; if (typeof options == 'object') Object.assign(myOptions, options); try { const invoiceOut = await models.InvoiceOut.findById(id, null, myOptions); const issued = invoiceOut.issued; const year = issued.getFullYear().toString(); const month = (issued.getMonth() + 1).toString(); const day = issued.getDate().toString(); const container = await models.InvoiceContainer.container(year); const rootPath = container.client.root; const src = path.join(rootPath, year, month, day); const fileName = `${year}${invoiceOut.ref}.pdf`; const fileSrc = path.join(src, fileName); const file = { path: fileSrc, contentType: 'application/pdf', name: fileName }; try { await fs.access(file.path); } catch (error) { await Self.createPdf(ctx, id); } const stream = fs.createReadStream(file.path); return [stream, file.contentType, `filename="${file.name}"`]; } catch (error) { if (error.code === 'ENOENT') throw new UserError('The PDF document does not exists'); throw error; } }; };