mozilla/pdf.js · error · Error
doc.info.${prop} is read-only
Error message
doc.info.${prop} is read-only What it means
`doc.info` is a `Proxy` (handler `InfoProxyHandler` in doc.js) over the document's Info dictionary: title, author, authors, subject, keywords, creator, producer, creationdate, moddate, trapped. Reads are case-insensitive; the `set` trap throws `Error("doc.info.${prop} is read-only")` for ANY written property name, interpolating the key. So even writing an unknown key throws.
Source
Thrown at src/scripting_api/doc.js:30
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { makeArr, makeMap, serializeError } from "./app_utils.js";
import { createMap } from "./common.js";
import { PDFObject } from "./pdf_object.js";
import { PrintParams } from "./print_params.js";
import { ZoomType } from "./constants.js";
const DOC_EXTERNAL = false;
class InfoProxyHandler {
static get(obj, prop) {
return obj[prop.toLowerCase()];
}
static set(obj, prop, value) {
throw new Error(`doc.info.${prop} is read-only`);
}
}
class Doc extends PDFObject {
#pageActions = null;
#otherPageActions = null;
constructor(data) {
super(data);
// In a script doc === this.
// So adding a property to the doc means adding it to this
this._expandos = globalThis;
this._baseURL = data.baseURL || "";
this._calculate = true;
this._delay = false;View on GitHub (pinned to 5903d58d58)
Solutions
- Do not assign to `doc.info.*`; treat it as read-only metadata.
- Set title/author/subject/keywords in the PDF's Info dictionary at authoring time and re-export.
- Wrap the assignment in try/catch if you must run untrusted/portable PDFs unchanged.
Example fix
// before doc.info.title = "Annual Report"; // after // info is read-only in pdf.js; set the title in the PDF's Info dictionary at creation, then read doc.info.title
Defensive patterns
Strategy: try-catch
Validate before calling
// doc.info is a Proxy whose set trap always throws; there is no // writable sub-property, so do not attempt any assignment to it. // Read-only access is safe: const title = doc.info.title;
Type guard
// Every key on doc.info is read-only -> the only safe operation is read. const isInfoWriteSafe = () => false;
Try / catch
try {
doc.info[prop] = value;
} catch (e) {
if (/doc\.info\..*is read-only/.test(e.message)) { /* expected; ignore */ }
else { throw e; }
} Prevention
- Never assign to `doc.info` or any of its sub-properties in pdf.js scripts.
- Edit metadata at the PDF source (Info dictionary), not from embedded JavaScript.
- If processing third-party PDFs, keep a try/catch boundary around sandboxed script execution.
When it happens
Trigger: Any sandboxed assignment to an info sub-property: `doc.info.Title = "x"`, `doc.info["author"] = "y"`, or `doc.info.custom = 1` (custom also throws because the trap is unconditional).
Common situations: Scripts ported from old Acrobat versions where info was mutable; forms that try to write the logged-in user into `doc.info.author` on save; metadata-stamping scripts.
Related errors
- doc.author is read-only
- doc.bookmarkRoot is read-only
- doc.creator is read-only
- doc.dataObjects is read-only
- doc.docID is read-only
AI-assisted analysis of mozilla/pdf.js@5903d58d58 (2026-08-13).
Data as JSON: /api/errors/d56257c26219bb0d.
Report an issue: GitHub.