mirror of
https://github.com/alam00000/bentopdf.git
synced 2026-11-09 17:14:16 +01:00
- Refactor PDF loading across workflow nodes to use loadPdfDocument utility
- Replaced direct calls to PDFDocument.load with loadPdfDocument in multiple nodes to standardize PDF loading process.
This commit is contained in:
1 parent
9d362b1cf8
commit
9278774b8a
110 files changed
+1413
-1196
No files matched your search
@@ -97,7 +97,9 @@ export async function performCondenseCompression(
|
||||
return { ...result, usedFallback: true };
|
||||
} catch (fallbackError: any) {
|
||||
const msg = fallbackError?.message || String(fallbackError);
|
||||
throw new Error(`PDF compression failed: ${msg}`);
|
||||
throw new Error(`PDF compression failed: ${msg}`, {
|
||||
cause: fallbackError,
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,7 +52,8 @@ export async function loadGhostscript(): Promise<GhostscriptInterface> {
|
||||
} catch (error: any) {
|
||||
loadPromise = null;
|
||||
throw new Error(
|
||||
`Failed to load Ghostscript from ${normalizedUrl}: ${error.message}`
|
||||
`Failed to load Ghostscript from ${normalizedUrl}: ${error.message}`,
|
||||
{ cause: error }
|
||||
);
|
||||
}
|
||||
})();
|
||||
|
||||
@@ -4,12 +4,9 @@
|
||||
* Requires user to configure Ghostscript URL in WASM Settings.
|
||||
*/
|
||||
|
||||
import {
|
||||
getWasmBaseUrl,
|
||||
fetchWasmFile,
|
||||
isWasmAvailable,
|
||||
} from '../config/wasm-cdn-config.js';
|
||||
import { PDFDocument, PDFDict, PDFName, PDFArray } from 'pdf-lib';
|
||||
import { getWasmBaseUrl, isWasmAvailable } from '../config/wasm-cdn-config.js';
|
||||
import { PDFDict, PDFName, PDFArray } from 'pdf-lib';
|
||||
import { loadPdfDocument } from './load-pdf-document.js';
|
||||
|
||||
interface GhostscriptModule {
|
||||
FS: {
|
||||
@@ -160,7 +157,9 @@ export async function convertToPdfA(
|
||||
);
|
||||
} catch (e) {
|
||||
console.error('[Ghostscript] Failed to setup PDF/A assets:', e);
|
||||
throw new Error('Conversion failed: could not create PDF/A definition');
|
||||
throw new Error('Conversion failed: could not create PDF/A definition', {
|
||||
cause: e,
|
||||
});
|
||||
}
|
||||
|
||||
const args = [
|
||||
@@ -200,7 +199,7 @@ export async function convertToPdfA(
|
||||
exitCode = gs.callMain(args);
|
||||
} catch (e) {
|
||||
console.error('[Ghostscript] Exception:', e);
|
||||
throw new Error(`Ghostscript threw an exception: ${e}`);
|
||||
throw new Error(`Ghostscript threw an exception: ${e}`, { cause: e });
|
||||
}
|
||||
|
||||
console.log('[Ghostscript] Exit code:', exitCode);
|
||||
@@ -208,23 +207,23 @@ export async function convertToPdfA(
|
||||
if (exitCode !== 0) {
|
||||
try {
|
||||
gs.FS.unlink(inputPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(outputPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(iccPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(pdfaDefPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
throw new Error(`Ghostscript conversion failed with exit code ${exitCode}`);
|
||||
}
|
||||
@@ -237,29 +236,29 @@ export async function convertToPdfA(
|
||||
output = gs.FS.readFile(outputPath);
|
||||
} catch (e) {
|
||||
console.error('[Ghostscript] Failed to read output:', e);
|
||||
throw new Error('Ghostscript did not produce output file');
|
||||
throw new Error('Ghostscript did not produce output file', { cause: e });
|
||||
}
|
||||
|
||||
// Cleanup
|
||||
try {
|
||||
gs.FS.unlink(inputPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(outputPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(iccPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(pdfaDefPath);
|
||||
} catch {
|
||||
/* ignore */
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
|
||||
if (level !== 'PDF/A-1b') {
|
||||
@@ -282,8 +281,7 @@ export async function convertToPdfA(
|
||||
async function addPageGroupDictionaries(
|
||||
pdfData: Uint8Array
|
||||
): Promise<Uint8Array> {
|
||||
const pdfDoc = await PDFDocument.load(pdfData, {
|
||||
ignoreEncryption: true,
|
||||
const pdfDoc = await loadPdfDocument(pdfData, {
|
||||
updateMetadata: false,
|
||||
});
|
||||
|
||||
@@ -352,7 +350,7 @@ async function addPageGroupDictionaries(
|
||||
}
|
||||
|
||||
if (iccProfileRef) {
|
||||
pdfDoc.context.enumerateIndirectObjects().forEach(([ref, obj]) => {
|
||||
pdfDoc.context.enumerateIndirectObjects().forEach(([_ref, obj]) => {
|
||||
if (
|
||||
obj instanceof PDFDict ||
|
||||
(obj && typeof obj === 'object' && 'dict' in obj)
|
||||
@@ -437,17 +435,23 @@ export async function convertFontsToOutlines(
|
||||
} catch (e) {
|
||||
try {
|
||||
gs.FS.unlink(inputPath);
|
||||
} catch {}
|
||||
throw new Error(`Ghostscript threw an exception: ${e}`);
|
||||
} catch (e2) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e2);
|
||||
}
|
||||
throw new Error(`Ghostscript threw an exception: ${e}`, { cause: e });
|
||||
}
|
||||
|
||||
if (exitCode !== 0) {
|
||||
try {
|
||||
gs.FS.unlink(inputPath);
|
||||
} catch {}
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(outputPath);
|
||||
} catch {}
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
throw new Error(`Ghostscript conversion failed with exit code ${exitCode}`);
|
||||
}
|
||||
|
||||
@@ -455,15 +459,19 @@ export async function convertFontsToOutlines(
|
||||
try {
|
||||
output = gs.FS.readFile(outputPath);
|
||||
} catch (e) {
|
||||
throw new Error('Ghostscript did not produce output file');
|
||||
throw new Error('Ghostscript did not produce output file', { cause: e });
|
||||
}
|
||||
|
||||
try {
|
||||
gs.FS.unlink(inputPath);
|
||||
} catch {}
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
try {
|
||||
gs.FS.unlink(outputPath);
|
||||
} catch {}
|
||||
} catch (e) {
|
||||
console.warn('[Ghostscript] Failed to clean up temp file:', e);
|
||||
}
|
||||
|
||||
return output;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
import { PDFDocument } from 'pdf-lib';
|
||||
|
||||
type LoadOptions = Parameters<typeof PDFDocument.load>[1];
|
||||
type PDFDocumentInstance = Awaited<ReturnType<typeof PDFDocument.load>>;
|
||||
|
||||
export async function loadPdfDocument(
|
||||
pdf: Uint8Array | ArrayBuffer,
|
||||
options?: LoadOptions
|
||||
): Promise<PDFDocumentInstance> {
|
||||
return PDFDocument.load(pdf, {
|
||||
ignoreEncryption: true,
|
||||
...options,
|
||||
});
|
||||
}
|
||||
@@ -1,11 +1,12 @@
|
||||
import { PDFDocument, degrees, rgb, StandardFonts, PageSizes } from 'pdf-lib';
|
||||
import { loadPdfDocument } from './load-pdf-document.js';
|
||||
|
||||
export async function mergePdfs(
|
||||
pdfBytesList: Uint8Array[]
|
||||
): Promise<Uint8Array> {
|
||||
const mergedDoc = await PDFDocument.create();
|
||||
for (const bytes of pdfBytesList) {
|
||||
const srcDoc = await PDFDocument.load(bytes);
|
||||
const srcDoc = await loadPdfDocument(bytes);
|
||||
const copiedPages = await mergedDoc.copyPages(
|
||||
srcDoc,
|
||||
srcDoc.getPageIndices()
|
||||
@@ -19,7 +20,7 @@ export async function splitPdf(
|
||||
pdfBytes: Uint8Array,
|
||||
pageIndices: number[]
|
||||
): Promise<Uint8Array> {
|
||||
const srcDoc = await PDFDocument.load(pdfBytes);
|
||||
const srcDoc = await loadPdfDocument(pdfBytes);
|
||||
const newPdf = await PDFDocument.create();
|
||||
const copiedPages = await newPdf.copyPages(srcDoc, pageIndices);
|
||||
copiedPages.forEach((page) => newPdf.addPage(page));
|
||||
@@ -30,7 +31,7 @@ export async function rotatePdfUniform(
|
||||
pdfBytes: Uint8Array,
|
||||
angle: number
|
||||
): Promise<Uint8Array> {
|
||||
const srcDoc = await PDFDocument.load(pdfBytes);
|
||||
const srcDoc = await loadPdfDocument(pdfBytes);
|
||||
const newPdfDoc = await PDFDocument.create();
|
||||
const pageCount = srcDoc.getPageCount();
|
||||
|
||||
@@ -75,7 +76,7 @@ export async function rotatePdfPages(
|
||||
pdfBytes: Uint8Array,
|
||||
rotations: number[]
|
||||
): Promise<Uint8Array> {
|
||||
const srcDoc = await PDFDocument.load(pdfBytes);
|
||||
const srcDoc = await loadPdfDocument(pdfBytes);
|
||||
const newPdfDoc = await PDFDocument.create();
|
||||
const pageCount = srcDoc.getPageCount();
|
||||
|
||||
@@ -121,7 +122,7 @@ export async function deletePdfPages(
|
||||
pdfBytes: Uint8Array,
|
||||
pagesToDelete: Set<number>
|
||||
): Promise<Uint8Array> {
|
||||
const srcDoc = await PDFDocument.load(pdfBytes);
|
||||
const srcDoc = await loadPdfDocument(pdfBytes);
|
||||
const totalPages = srcDoc.getPageCount();
|
||||
|
||||
const pagesToKeep: number[] = [];
|
||||
@@ -196,7 +197,7 @@ export async function addTextWatermark(
|
||||
pdfBytes: Uint8Array,
|
||||
options: TextWatermarkOptions
|
||||
): Promise<Uint8Array> {
|
||||
const pdfDoc = await PDFDocument.load(pdfBytes);
|
||||
const pdfDoc = await loadPdfDocument(pdfBytes);
|
||||
|
||||
const canvas = document.createElement('canvas');
|
||||
const ctx = canvas.getContext('2d');
|
||||
@@ -274,7 +275,7 @@ export async function addImageWatermark(
|
||||
pdfBytes: Uint8Array,
|
||||
options: ImageWatermarkOptions
|
||||
): Promise<Uint8Array> {
|
||||
const pdfDoc = await PDFDocument.load(pdfBytes);
|
||||
const pdfDoc = await loadPdfDocument(pdfBytes);
|
||||
const image =
|
||||
options.imageType === 'png'
|
||||
? await pdfDoc.embedPng(options.imageBytes)
|
||||
@@ -330,7 +331,7 @@ export async function addPageNumbers(
|
||||
pdfBytes: Uint8Array,
|
||||
options: PageNumberOptions
|
||||
): Promise<Uint8Array> {
|
||||
const pdfDoc = await PDFDocument.load(pdfBytes);
|
||||
const pdfDoc = await loadPdfDocument(pdfBytes);
|
||||
const helveticaFont = await pdfDoc.embedFont(StandardFonts.Helvetica);
|
||||
const pages = pdfDoc.getPages();
|
||||
const totalPages = pages.length;
|
||||
@@ -481,7 +482,7 @@ export async function fixPageSize(
|
||||
[targetWidth, targetHeight] = [targetHeight, targetWidth];
|
||||
}
|
||||
|
||||
const sourceDoc = await PDFDocument.load(pdfBytes);
|
||||
const sourceDoc = await loadPdfDocument(pdfBytes);
|
||||
const outputDoc = await PDFDocument.create();
|
||||
|
||||
for (const sourcePage of sourceDoc.getPages()) {
|
||||
|
||||
@@ -67,7 +67,9 @@ export async function loadPyMuPDF(): Promise<any> {
|
||||
return cachedPyMuPDF;
|
||||
} catch (error: any) {
|
||||
loadPromise = null;
|
||||
throw new Error(`Failed to load PyMuPDF from CDN: ${error.message}`);
|
||||
throw new Error(`Failed to load PyMuPDF from CDN: ${error.message}`, {
|
||||
cause: error,
|
||||
});
|
||||
}
|
||||
})();
|
||||
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { PDFDocument, PDFName } from 'pdf-lib';
|
||||
import { loadPdfDocument } from './load-pdf-document.js';
|
||||
|
||||
export interface SanitizeOptions {
|
||||
flattenForms: boolean;
|
||||
@@ -503,7 +504,7 @@ export async function sanitizePdf(
|
||||
pdfBytes: Uint8Array,
|
||||
options: SanitizeOptions
|
||||
): Promise<{ pdfDoc: PDFDocument; bytes: Uint8Array }> {
|
||||
const pdfDoc = await PDFDocument.load(pdfBytes);
|
||||
const pdfDoc = await loadPdfDocument(pdfBytes);
|
||||
|
||||
if (options.flattenForms) {
|
||||
try {
|
||||
|
||||
Reference in new issue
Block a user