Under the Hood: The Architecture of Text to PDF Converter
Most “text to PDF online” products POST the body to a typesetting worker, cache a download URL, and retain drafts for “history.” That is a document leak for contracts and notes. This converter never leaves the tab. You paste (or optionally decode a .txt with the File API). pdf-lib creates a PDFDocument, embeds StandardFonts.Helvetica, wraps lines with widthOfTextAtSize, paginates Letter or A4, and save() emits bytes. A Blob plus URL.createObjectURL streams the file to disk.
It is not OCR and not Markdown-to-PDF. The job is convert text to PDF: the glyphs you typed become content streams. No telemetry of the body, no server-side cache of notepad-to-PDF jobs.
Memory Allocation & Browser Threading Mechanics
The source is one JS string. WinAnsi mapping allocates a second string of similar length. Wrapping produces an array of line strings; peak extra memory is O(lines). Font metrics are looked up in the embedded Helvetica program (a small table). Drawing is sequential: one page object at a time, so a 100-page dump does not hold 100 canvases. The main thread runs the loop; typical notes finish in one animation frame. Huge pastes can hitch—there is no Worker because pdf-lib expects a document on this realm.
Algorithmic Deep-Dive: Code Snippet & Logical Analysis
const font = await doc.embedFont(StandardFonts.Helvetica);
const maxWidth = pageWidth - margin * 2;
function wrapLine(text, size) {
const words = text.split(/(\s+)/);
const lines = [];
let current = "";
for (const word of words) {
const next = current + word;
if (font.widthOfTextAtSize(next, size) <= maxWidth || !current) current = next;
else { lines.push(current.trimEnd()); current = word.trimStart(); }
}
if (current) lines.push(current.trimEnd());
return lines;
}
page.drawText(line, { x: margin, y, size, font });Word-boundary wrap beats the earlier character-chunk hack used on the notepad PDF export: a long token that exceeds maxWidth is still placed (otherwise the loop would stall). Empty source lines become blank leading. When y drops below the bottom margin, addPage resets y. Unsupported Unicode is mapped to ASCII punctuation or question marks so Helvetica encoding does not throw. That is a typesetting limit of StandardFonts, not a network failure.
The Local Storage Sandbox & Volatile Data Pipelines
React holds the textarea and print settings only. The PDFDocument is unreachable after save(). The download Blob is revoked after click. No IndexedDB of generated PDFs. Closing the tab drops the draft.
Verifying True Privacy: How to Audit Your Browser's Network Tab
F12, Network, clear. Paste a unique sentence, Download PDF. Search the HAR for that sentence. Zero request bodies. You should not see a multipart file POST. pdf-lib is a JS module already on the origin, not a conversion API.