UNPKG

pdf-to-png-converter

Version:

Node.js utility to convert PDF file/buffer pages to PNG files/buffers. No build-time compilation required — pre-built native binaries included for all major platforms.

153 lines (152 loc) 8.2 kB
import type { VerbosityLevel } from '../types/index.js'; /** * Options for the `pdfToPng` conversion function. * * All properties are optional. Any unset property falls back to the corresponding * value in `PDF_TO_PNG_OPTIONS_DEFAULTS` defined in `src/const.ts`. */ export interface PdfToPngOptions { /** * Scale factor applied to each page viewport before rendering. * Values above `1` produce larger, higher-resolution images; values below `1` produce smaller images. * Must be a finite positive number. Maximum allowed value is `100`; values above this limit throw * immediately to prevent runaway memory allocation (OOM) during canvas creation. * Default: `1`. */ viewportScale?: number; /** * When `true`, pdfjs will not load embedded fonts and substitutes them with built-in fonts. * Speeds up rendering but may affect visual fidelity for PDFs with custom fonts. * Default: `true`. */ disableFontFace?: boolean; /** * When `true`, pdfjs attempts to use fonts installed on the host system. * Typically combined with `disableFontFace: false` to improve font rendering accuracy. * Default: `false`. */ useSystemFonts?: boolean; /** * When `true`, pdfjs processes XFA (XML Forms Architecture) form data embedded in the PDF. * Default: `true`. */ enableXfa?: boolean; /** * Password for opening password-protected (encrypted) PDFs. * Leave `undefined` for unprotected files. * Default: `undefined`. */ pdfFilePassword?: string; /** * Folder path (relative or absolute) where PNG files will be written. * Relative paths are resolved against `process.cwd()`. * The folder is created recursively if it does not exist. * When omitted, no files are written to disk. * * @remarks * **Security (TOCTOU):** The write-containment guard rejects filenames that contain path * separators (so the target is always a direct child of this folder), resolves symlinks, * checks that the output path stays within this folder, and uses exclusive-create file opens * to avoid overwriting pre-existing files or following a pre-planted target symlink at the * final filename. To reduce exposure on multi-user or shared systems, ensure this directory * is private and not writable by untrusted users. */ outputFolder?: string; /** * Custom naming function for output PNG files. * Receives the 1-based page number and must return a full filename string including the `.png` extension * (e.g. `(pageNumber) => \`page_${pageNumber}.png\``). * When omitted, names default to `<pdfBasename>_page_<pageNumber>.png`, * or `buffer_page_<pageNumber>.png` when the PDF is supplied as an `ArrayBufferLike`. * @since 3.14.0 */ outputFileMaskFunc?: (pageNumber: number) => string; /** * 1-based integer page numbers to convert. Non-integer values and values less than or equal to zero throw immediately. * Pages above the document page count are silently ignored. * When omitted, all pages in the document are processed. * @since 3.3.0 */ pagesToProcess?: number[]; /** * pdfjs verbosity level. Use the `VerbosityLevel` const for readable values: * `VerbosityLevel.ERRORS` (0), `VerbosityLevel.WARNINGS` (1), `VerbosityLevel.INFOS` (5). * Default: `VerbosityLevel.ERRORS` (0). */ verbosityLevel?: VerbosityLevel; /** * When `true`, each `PngPageOutput` will include a `content` property containing the PNG image as a `Buffer`. * Set to `false` to skip buffering when only writing files to disk, which reduces memory usage. * Default: `true`. */ returnPageContent?: boolean; /** * When `true`, only page metadata is returned for each page without rendering any PNG image. * The returned `PngPageOutput` objects will have `pageNumber`, `name`, `width`, `height`, and * `rotation` populated, but `content` will always be `undefined` and `path` will always be `""`. * No canvas is created, no rendering is performed, and no files are written to disk even if * `outputFolder` is set. * This is significantly faster than full rendering and useful for inspecting page dimensions * and rotation without generating images. * To stay consistent with a real render, this path still rejects pages that could not be * rendered at the requested `viewportScale` — both those that floor to `0` px and those whose * rendered (floored) canvas area exceeds the internal canvas pixel limit — rather than reporting * dimensions for a page that would throw on render. * Default: `false`. * @since 3.14.0 */ returnMetadataOnly?: boolean; /** * When `true`, selected pages are rendered concurrently through a sliding-window scheduler * that keeps up to `concurrencyLimit` pages active. When `false`, pages are processed in * a lightly pipelined sequence: results are always returned in page order, but the PNG * encoding and disk writes of finished pages may overlap the rendering of the next page * (at most three pages in flight), so files may finish writing out of page order and, when * a page fails, pages already in flight still complete before the returned promise rejects. * Consume output via the resolved `PngPageOutput[]` (ordered) rather than directory-watch order. * Peak canvas memory in this mode is up to three live canvases; for strict one-page-at-a-time * processing with a single live canvas, set `processPagesInParallel: true` with * `concurrencyLimit: 1` (a sliding window of exactly one page). * Default: `false`. * @since 3.7.0 */ processPagesInParallel?: boolean; /** * Maximum number of pages rendered simultaneously when `processPagesInParallel` is `true`. * Must be a positive integer between `1` and `16` (inclusive); values outside that range throw * immediately (before any I/O). The upper bound caps peak in-flight canvas memory at roughly * `16 × MAX_CANVAS_PIXELS × 4 bytes ≈ 6.4 GiB` so a single conversion cannot exhaust container * memory. Higher values increase throughput at the cost of memory. Applies when * `processPagesInParallel` or `renderInWorkerThreads` is enabled; in worker-thread mode it * sets the worker-pool size. * Default: `4`. * @since 3.14.0 */ concurrencyLimit?: number; /** * When `true`, pages are rasterized in a pool of Node.js worker threads (pool size = * `concurrencyLimit`), giving true multi-core parallelism — unlike `processPagesInParallel`, * which interleaves pages on one thread. Each worker loads its own copy of the document, so * expect roughly one PDF copy plus one pdf.js instance of memory per worker and a pool * startup cost of a few hundred milliseconds per conversion; it pays off on multi-page, * render-heavy (e.g. image-heavy) documents and can be slower for small ones. * Rendered pixels are identical to single-threaded mode; results are returned in page * order; disk writes still happen on the main thread through the same path-security guards. * Takes precedence over `processPagesInParallel`. Ignored when `returnMetadataOnly` is `true` * (metadata extraction does not render). `outputFileMaskFunc` is fully supported — names are * resolved on the main thread before dispatch. * Default: `false`. * @since 4.2.0 */ renderInWorkerThreads?: boolean; /** * Maximum allowed input PDF size in bytes. Inputs larger than this throw immediately, * before any rendering work is started. Applies to both the file path branch (validated via * `fs.stat()`) and the buffer / `Uint8Array` branch (validated via `byteLength`). The path * branch additionally rejects non-regular files (FIFOs, sockets, character devices such as * `/dev/zero`) to prevent unbounded reads. Must be a positive integer. * Default: `256 * 1024 * 1024` (256 MiB). * @since 4.1.0 */ maxInputBytes?: number; }