SecurityApi
The Security dialog, headless. protect() and removeProtection() need the export feature (password protection ships with the file) and refuse with FEATURE_NOT_LICENSED without it; isEncrypted, permissions and unlockOwnerPermissions() need none. Permissions you do not mention stay allowed. High-quality printing is a degree of printing: print: false denies printHighQuality too, and permissions reports it denied whenever print is. Encryption applies to the open document and reaches the file through doc.save() — nothing on disk changes until you write those bytes somewhere.
What the viewer does with a document's permissions. A document opened with its open (user) password grants only what its permissions allow, and the viewer honors them as Acrobat does. Opened with its owner password, protected in this session, or after unlockOwnerPermissions(password) succeeds, everything is allowed — the viewer follows an unlock at once, and the unlock outlives every later reload (an edit, an undo). When the document forbids comments (annotate), Highlight, Mark text, Note, Text box, Draw, the shapes, Stamp, Link and Erase are grayed out, and so are the selection bar's markups and Add a note. Changes (modify): Edit text, Add text, Image, Sign, Erase and the selection bar's Black out are grayed out; attachments cannot be added or removed. Changing pages (assemble): Manage pages is grayed out, the thumbnails offer no rotate, move, duplicate or delete, and bookmarks cannot be edited. Filling in (fillForms, which the comment right also grants): form fields show their values read-only. Printing (print): Print is grayed out, print() and Ctrl+P refuse, and the browser's own print command prints blank pages. Copying (copy): the selection bar's Copy is grayed out, and copying from the page or from a read-only field puts nothing on the clipboard. A grayed-out control stays where it is: its tooltip says why, and a tap, click or Enter on it shows the reason instead of acting. activateTool() and print() refuse what is forbidden with PERMISSION_DENIED; toolBlockedReason(tool) gives the reason for a host's own chrome. There is no option to lift these: only the owner password does.
The document API (doc.pages, doc.annotations, doc.forms.setValues, doc.save(), …) is your own code acting on the file and is not restricted: permissions are the author's stated intent for the _people_ reading the document: a reader restricts its users, not an application its own code. Every PDF SDK reads it the same way, so a host that wants its own code held to the permissions reads doc.security.permissions and decides. What your code saves keeps the encryption and the bits as they are.
Usage
await doc.security.protect({ userPassword: 'open-me', ownerPassword: 'change-me', permissions: { modify: false, copy: false }, }); const bytes = await doc.save(); // the protection lives in these bytes
Reading
DOCUMENT_CLOSED on a closed document.boolean DOCUMENT_CLOSED— read on a closed document.
if (doc.security.isEncrypted) badge.hidden = false;
DocumentPermissions with every entry present. printHighQuality is reported denied whenever print is. A getter: answers at once, and throws DOCUMENT_CLOSED on a closed document.Required<DocumentPermissions> print, printHighQuality, modify, copy, annotate, fillForms, extractForAccessibility and assemble, every entry present.DOCUMENT_CLOSED— read on a closed document.
// Hold your own code to the document's permissions if (!doc.security.permissions.modify) throw new Error('This document forbids changes');
Protection
ownerPassword that differs from userPassword. Protecting a signed document changes what the signature covers, so it would no longer verify: refused as Acrobat refuses, unless settings.invalidateSignatures, and once told, the session asks no more. Needs the export feature.| Parameter | Type | Description |
|---|---|---|
| settings | ProtectionSettings | userPassword (required to open the document at all; leave empty for a document anyone can open but only the owner can change), ownerPassword (required to change permissions or remove protection), permissions (a DocumentPermissions, all optional) and invalidateSignatures. |
Promise<void> INVALID_ARGUMENT— no password at all, or restricting anything without anownerPasswordthat differs fromuserPassword.INVALID_STATE— a signed document, unlesssettings.invalidateSignatures; or a progressive document still downloading.FEATURE_NOT_LICENSED— the license lacksexport.PAGE_ERROR— the document could not be encrypted.DOCUMENT_CLOSED— the document has been closed.
// Anyone can open it; only the owner can print or change it await doc.security.protect({ ownerPassword: 'change-me', permissions: { print: false, modify: false }, });
options.invalidateSignatures. Needs the export feature.| Parameter | Type | Description |
|---|---|---|
| options? | SignedDocumentOptions | { invalidateSignatures? }. |
Promise<void> INVALID_STATE— a signed document, unlessoptions.invalidateSignatures; or a progressive document still downloading.FEATURE_NOT_LICENSED— the license lacksexport.DOCUMENT_CLOSED— the document has been closed.
await doc.security.removeProtection(); const plain = await doc.save();
| Parameter | Type | Description |
|---|---|---|
| ownerPassword | string | The document's owner password. |
Promise<boolean> Whether the password was accepted.DOCUMENT_CLOSED— the document has been closed.
const unlocked = await doc.security.unlockOwnerPermissions(ownerPassword); if (!unlocked) showError('Wrong owner password');