diff --git a/package.json b/package.json index 532a201..38ea9ce 100755 --- a/package.json +++ b/package.json @@ -21,6 +21,7 @@ "bluebird": "^3.7.2", "body-parser": "^1.20.3", "cheerio": "^1.0.0", + "compress-pdf": "^0.5.3", "cookie-parser": "^1.4.7", "cors": "^2.8.5", "country-codes-list": "^2.0.0", diff --git a/prova_generato-stampabile.pdf b/prova_generato-stampabile.pdf deleted file mode 100644 index af484c7..0000000 Binary files a/prova_generato-stampabile.pdf and /dev/null differ diff --git a/src/server/modules/GenPdf.js b/src/server/modules/GenPdf.js index ccb02f3..0135f38 100644 --- a/src/server/modules/GenPdf.js +++ b/src/server/modules/GenPdf.js @@ -1,5 +1,7 @@ const puppeteer = require('puppeteer'); const path = require('path'); +const { exec } = require('child_process'); + const fs = require('fs').promises; const gs = require('ghostscript4js'); @@ -12,6 +14,8 @@ const { MyPage } = require('../models/mypage'); const tools = require('../tools/general'); const shared_consts = require('../tools/shared_nodejs'); +const { compress } = require('compress-pdf'); + class GenPdf { constructor(idapp) { this.idapp = idapp; @@ -42,26 +46,24 @@ class GenPdf { } async autoScroll(page) { - console.log('inizia a scrollare') + console.log('inizia a scrollare'); await page.evaluate(async () => { await new Promise((resolve) => { let totalHeight = 0; - console.log('autoScroll...') + console.log('autoScroll...'); const distance = 100; const timer = setInterval(() => { window.scrollBy(0, distance); totalHeight += distance; - + if (totalHeight >= document.body.scrollHeight) { clearInterval(timer); resolve(); } }, 40); - - }); }); - console.log(' FINE: autoScroll...') + console.log(' FINE: autoScroll...'); } async generatePdfFromUrl(url, filenameOut, options = {}) { @@ -70,23 +72,37 @@ class GenPdf { } const page = await this.browser.newPage(); + const maxTentativi = 3; try { + console.log(`caricamento pagina: ${url}`); await page.goto(url, { waitUntil: 'networkidle0' }); await tools.attendiNSecondi(5); - await page.waitForSelector('#q-notify', { timeout: 60000 }); + let success = false; + let numTentativi1 = 0; + while (numTentativi1 < maxTentativi) { + try { + await page.waitForSelector('.pdf-section', { timeout: 10000 }); + success = true; + break; + } catch (e) { + console.log(`Tentativo ${numTentativi1 + 1}/${maxTentativi} fallito, ASPETTO DI PIU 10 secondi`); + await tools.attendiNSecondi(10); + } + numTentativi1++; + } await this.autoScroll(page); - + await tools.attendiNSecondi(5); - // Seleziona tutte le sezioni da stampare let sectionHandles = await page.$$('.pdf-section'); let numTentativi = 0; - const maxTentativi = 3; while (sectionHandles.length === 0 && numTentativi < maxTentativi) { - console.log(`Nessuna sezione .pdf-section trovata nella pagina, quindi ASPETTO DI PIU ${numTentativi + 1}/${maxTentativi}`); + console.log( + `Nessuna sezione .pdf-section trovata nella pagina, quindi ASPETTO DI PIU ${numTentativi + 1}/${maxTentativi}` + ); await tools.attendiNSecondi(5); sectionHandles = await page.$$('.pdf-section'); numTentativi++; @@ -113,8 +129,7 @@ class GenPdf { height: el.scrollHeight, // piccolo padding })); - console.log(`Larghezza: ${width}px, Altezza: ${height}px`); - + // console.log(`Larghezza: ${width}px, Altezza: ${height}px`); // Imposta viewport dinamico await page.setViewport({ width, height }); @@ -151,6 +166,9 @@ class GenPdf { console.log(`PDF finale generato: ${finalFilePath}`); + if (options.compressione) { + } + return finalFilePath; } catch (error) { console.error('Errore durante generazione PDF:', error); @@ -361,6 +379,8 @@ class GenPdf { } let filenamerelative = ''; let fullnamepath = ''; + let fullnamepath_compr = ''; + let filenamerelative_compressed = ''; let stampa = options.stampa; /*if (stampa) { @@ -373,28 +393,71 @@ class GenPdf { const catalog = await Catalog.findById(options.idCatalog); if (catalog) { - const url = tools.getHostByIdApp(this.idapp) + '/cataloghi?id=' + catalog._id + '&stampa=' + (stampa ? '1' : '0'); + const url = + tools.getHostByIdApp(this.idapp) + '/cataloghi?id=' + catalog._id + '&stampa=' + (stampa ? '1' : '0') + '&hideHeader=1'; if (url) { const myfilenameout = await this.getPathByPage(catalog.idPageAssigned); - - let addstr = (stampa) ? '_stampabile' : ''; + let addstr = stampa ? '_stampabile' : ''; filenamerelative = options.path + `${myfilenameout}${addstr}_generato.pdf`; fullnamepath = tools.getdirByIdApp(this.idapp) + '/' + filenamerelative; await this.generatePdfFromUrl(url, fullnamepath, options); + + if (options.comprimi) { + filenamerelative_compressed = options.path + `${myfilenameout}${addstr}_generato_compressed.pdf`; + fullnamepath_compr = tools.getdirByIdApp(this.idapp) + '/' + filenamerelative_compressed; + await this.compressPdf(fullnamepath, fullnamepath_compr, options.compressione); + } } } - return {fileout: filenamerelative, filesize: await tools.getSizeFile(fullnamepath)}; + return { + fileout: filenamerelative, + fileout_compressed: filenamerelative_compressed, + filesize: await tools.getSizeFile(fullnamepath), + filesize_compressed: await tools.getSizeFile(fullnamepath_compr), + }; } catch (error) { console.error('Errore durante la generazione del PDF dal catalogo ID:', error); - return {fileout: '', filesize: 0, error: 'Errore durante la generazione del PDF dal catalogo ID:' + error?.message}; + return { + fileout: '', + filesize: 0, + error: 'Errore durante la generazione del PDF dal catalogo ID:' + error?.message, + }; } - return {fileout: '', filesize: 0 }; + return { fileout: '', filesize: 0 }; + } + + async compressPdf(inputPath, outputPath, compressione = 'printer') { + return new Promise((resolve, reject) => { + // Risolvi i percorsi assoluti + const inputFile = path.resolve(inputPath); + const outputFile = path.resolve(outputPath); + + const validQualities = ['screen', 'ebook', 'printer', 'prepress', 'default']; + if (!validQualities.includes(compressione)) compressione = 'screen'; + + // Comando Ghostscript per compressione - impostazione per web (/screen) + const gsCommand = `gs -sDEVICE=pdfwrite -dCompatibilityLevel=1.4 -dPDFSETTINGS=/${compressione} -dNOPAUSE -dBATCH -dQUIET -sOutputFile="${outputFile}" "${inputFile}"`; + + console.log('Eseguo comando:', gsCommand); + + exec(gsCommand, (error, stdout, stderr) => { + if (error) { + console.error(`Errore compressione PDF: ${error.message}`); + return reject(error); + } + if (stderr) { + console.error(`Ghostscript stderr: ${stderr}`); + } + console.log(`Compressione completata. File salvato in: ${outputFile}`); + resolve(outputFile); + }); + }); } } diff --git a/yarn.lock b/yarn.lock index 3c738dd..0c6ed9d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2363,6 +2363,14 @@ component-emitter@^1.3.0: resolved "https://registry.yarnpkg.com/component-emitter/-/component-emitter-1.3.1.tgz#ef1d5796f7d93f135ee6fb684340b26403c97d17" integrity sha512-T0+barUSQRTUQASh8bx02dl+DhF54GtIDY13Y3m9oWTklKbb3Wv974meRpeZ3lp1JpLVECWWNHC4vaG2XHXouQ== +compress-pdf@^0.5.3: + version "0.5.3" + resolved "https://registry.yarnpkg.com/compress-pdf/-/compress-pdf-0.5.3.tgz#15a8c5d43f2241437a1ad42306955ccb9319367e" + integrity sha512-LeDPmE+o0PwxzqLU/uGIsaLxmnzZy4lXaY0tBov03uhNgXV6dZjU3VTBy3LhAhiCV+moXyBBE9kCDOZzZcEobg== + dependencies: + dotenv "16.4.7" + lodash "4.17.21" + concat-map@0.0.1: version "0.0.1" resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" @@ -3009,7 +3017,7 @@ domutils@^3.0.1, domutils@^3.1.0: domelementtype "^2.3.0" domhandler "^5.0.3" -dotenv@^16.4.7: +dotenv@16.4.7, dotenv@^16.4.7: version "16.4.7" resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-16.4.7.tgz#0e20c5b82950140aa99be360a8a5f52335f53c26" integrity sha512-47qPchRCykZC03FhkYAhrvwU4xDBFIj1QPqaarj6mdM/hgUzfPHcpkHJOn3mJAufFeeAxAzeGsr5X0M4k6fLZQ== @@ -5957,7 +5965,7 @@ lodash.some@^4.4.0: resolved "https://registry.yarnpkg.com/lodash.some/-/lodash.some-4.6.0.tgz#1bb9f314ef6b8baded13b549169b2a945eb68e4d" integrity sha512-j7MJE+TuT51q9ggt4fSgVqro163BEFjAt3u97IqU+JA2DkWl80nFTrowzLpZ/BnpN7rrl0JA/593NAdd8p/scQ== -lodash@^4.17.10, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.21: +lodash@4.17.21, lodash@^4.17.10, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.21: version "4.17.21" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==