The engine
@cloudpdf/engine is the cloud client for CloudPDF. It implements the same
Engine interface as the local WASM engine that powers EmbedPDF, but instead of
running PDFium in a Web Worker it routes every call over HTTPS to a
@cloudpdf/server deployment (self-hosted or CloudPDF SaaS).
That means the same SDK code that drives a fully local viewer also drives a cloud-backed one — only the transport differs. You get document open, page rendering, text extraction, annotations, metadata, and security/access through a single, abortable, strongly-typed API.
These pages assume a reachable CloudPDF deployment — the managed SaaS or your
own @cloudpdf/server — and every example talks to it over HTTPS.
Prefer running fully in the browser, with no server at all? That’s the
local WASM engine — the same
Engine API and the same plugins, powered by @embedpdf/engine.
New here? Jump to the Quick start to open a document and render its first page in a few lines of code.
What the engine gives you#
- One
Enginecontract —createCloudEngine(...)returns an object with a singleopen()method that resolves to aDocumentHandle. - Document handles — a
DocumentHandleexposesmetadata,annotations,pages,security, and apage(pon)accessor for per-page work. - Rendering — request a page as an encoded image (
png/webp) or raw RGBA, at any scale or target rectangle. - Text & geometry — extract a page’s plain text or geometry snapshot.
- Annotations — list, create, update, delete, and reorder annotations.
- Security & access — inspect encryption/permission state, unlock password-protected documents, and read the caller’s effective scope.
- Abortable everything — every async call returns an
AbortablePromiseyou can cancel, with typedEngineErrors on failure.
How it fits together#
import { createCloudEngine } from '@cloudpdf/engine';
const engine = createCloudEngine({
baseUrl: 'https://pdf.your-app.com',
token: () => getDocToken(), // doc-scoped JWT from your backend
});
const doc = await engine.open({ kind: 'token', token: () => getDocToken() });
const page = doc.page(/* pageObjectNumber */ 4);
const image = await page.render.image({ viewport: { kind: 'width', width: 1200 } });
const { url, revoke } = await image.objectUrl();
// …draw `url` into an <img>, then revoke() when done.
await doc.close();
await engine.destroy();Your backend mints the short-lived, document-scoped JWT; the browser never sees storage credentials or your tenant secret.