@asterdoc/render 0.0.0-stage → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/pdf.d.ts ADDED
@@ -0,0 +1,620 @@
1
+ import { BinaryContent, Form, Formatter, LayerFormat, AsterdocRenderer, RendererLayer, LocateHit } from '@asterdoc/types';
2
+ export { LocateHit } from '@asterdoc/types';
3
+ import { P as PdfFont } from './layer-bindings-CFXyN7SM.js';
4
+ export { a as PdfBindingKeyError, b as PdfBindingPart, c as PdfBindingSyntaxError, d as PdfFontError, e as PdfFontMetrics, F as PdfFontProblem, p as parseBinding, f as pdfFontMetrics } from './layer-bindings-CFXyN7SM.js';
5
+
6
+ /** Why a value could not be drawn in its PDF form field or overlay. */
7
+ type PdfFieldFillReason = 'overflow' | 'comb-length' | 'missing-glyph' | 'unsupported-script';
8
+ /** What a {@link PdfFieldFillError} reports beyond the field and the reason. */
9
+ interface PdfFieldFillDetail {
10
+ /** For `overflow`, the minimum font size in points; for `comb-length`, the number of comb boxes. */
11
+ limit?: number;
12
+ /** For `missing-glyph`, the character no available font can draw. */
13
+ character?: string;
14
+ /** For `unsupported-script`, the script that needs glyph shaping. */
15
+ script?: string;
16
+ }
17
+ /**
18
+ * Thrown when a value cannot be drawn faithfully in a PDF form field or a text
19
+ * overlay, naming the field and why.
20
+ */
21
+ declare class PdfFieldFillError extends Error {
22
+ /** Fully qualified name of the PDF form field, or the overlay that failed. */
23
+ readonly field: string;
24
+ readonly reason: PdfFieldFillReason;
25
+ readonly limit?: number;
26
+ readonly character?: string;
27
+ readonly script?: string;
28
+ constructor(field: string, reason: PdfFieldFillReason, detail: PdfFieldFillDetail, message: string);
29
+ }
30
+ /** Smallest size a value shrinks to before filling fails with an overflow error. */
31
+ declare const MIN_FONT_SIZE = 6;
32
+
33
+ /**
34
+ * Thrown by every entry point that parses or writes a PDF when the file is
35
+ * encrypted.
36
+ *
37
+ * An encrypted file stores its strings and streams enciphered under a key
38
+ * derived from the file itself. Field names read as ciphertext, values written
39
+ * in plaintext would not decrypt, and copied streams would be garbage, so an
40
+ * encrypted file is refused rather than read wrongly.
41
+ */
42
+ declare class PdfEncryptedError extends Error {
43
+ readonly code: "encrypted_pdf";
44
+ constructor();
45
+ }
46
+
47
+ /** What kind of control an AcroForm field is, read from its `/FT` and `/Ff`. */
48
+ type PdfFieldType = 'text' | 'checkbox' | 'dropdown' | 'radio' | 'button' | 'signature' | 'unknown';
49
+
50
+ interface PdfFieldInfo {
51
+ name: string;
52
+ type: PdfFieldType;
53
+ value?: string | boolean | string[];
54
+ required?: boolean;
55
+ page?: number;
56
+ rect?: [number, number, number, number];
57
+ maxLen?: number | null;
58
+ }
59
+ interface InspectOptions {
60
+ includeButton?: boolean;
61
+ includeSignature?: boolean;
62
+ }
63
+ interface PdfPageInfo {
64
+ /** One-based page number. */
65
+ page: number;
66
+ /** Page width in PDF points. */
67
+ width: number;
68
+ /** Page height in PDF points. */
69
+ height: number;
70
+ }
71
+ interface PdfInfo {
72
+ pageCount: number;
73
+ pages: PdfPageInfo[];
74
+ }
75
+ /** Inspect page count and dimensions without loading a full PDF toolkit. */
76
+ declare function inspectPdf(template: BinaryContent): Promise<PdfInfo>;
77
+ /** List the AcroForm fields a PDF declares, walked as fill walks them. */
78
+ declare function inspectAcroFormFields(template: BinaryContent, options?: InspectOptions): Promise<PdfFieldInfo[]>;
79
+
80
+ /**
81
+ * Burn AcroForm widget appearances into their pages and remove the interactive
82
+ * form controls. A widget a viewer does not show (Hidden or NoView) is removed
83
+ * without being drawn. PDFs without an AcroForm are returned unchanged.
84
+ */
85
+ declare function flattenPdf(template: BinaryContent): Promise<Uint8Array>;
86
+
87
+ /**
88
+ * One PDF from several, page for page.
89
+ *
90
+ * A packet is a sequence of documents a reader sees as one file, and one file
91
+ * is what a hash and a signature map describe. Merging is how the sequence
92
+ * becomes that file.
93
+ *
94
+ * The merge writes a fresh document rather than appending an incremental
95
+ * update, because two sources number their objects from one and an incremental
96
+ * update has no way to hold both. Every object a kept page can reach is copied
97
+ * with a new number, every reference inside it is rewritten to that number, and
98
+ * a new catalog and page tree are written over the result. Stream bytes are
99
+ * copied exactly as they were stored, filters and all, so nothing is
100
+ * re-encoded and nothing is re-rendered.
101
+ *
102
+ * **What a merge drops.** Everything the old catalog held rather than the page:
103
+ *
104
+ * - the interactive form (`AcroForm`), so flatten a filled form before merging
105
+ * it and its values arrive as page content;
106
+ * - the structure tree (`StructTreeRoot`) and the role map, which is the
107
+ * document's accessibility tagging. A copied page keeps its `StructParents`
108
+ * key, which then points at a tree that is no longer there. A reader ignores
109
+ * a dangling `StructParents`; a screen reader gets untagged pages;
110
+ * - the name tree (`Names`) and `Dests`, so a named destination no longer
111
+ * resolves and a link that used one goes nowhere;
112
+ * - optional content (`OCProperties`), so a page drawn with layers loses the
113
+ * configuration that decides which are visible, and every layer paints;
114
+ * - `Lang`, `ViewerPreferences`, `Outlines`, `PageLabels`, `Metadata` and
115
+ * `PageMode`.
116
+ *
117
+ * A packet is assembled from documents that are already final, and none of
118
+ * those survive a print either, which is what makes the trade acceptable here.
119
+ * A caller who needs any of them should say so rather than merge.
120
+ */
121
+
122
+ /** Thrown when a source cannot be merged, naming which one and why. */
123
+ declare class PdfMergeError extends Error {
124
+ /** Zero-based position of the offending source in the input. */
125
+ readonly source: number;
126
+ constructor(source: number, detail: string);
127
+ }
128
+ /**
129
+ * Concatenate PDFs into one document, keeping every page in the order given.
130
+ *
131
+ * A single source is returned unchanged, so merging a one-part packet costs
132
+ * nothing and produces the bytes the part already had.
133
+ *
134
+ * @throws {PdfEncryptedError} when a source is encrypted.
135
+ * @throws {PdfMergeError} naming the source, when it has no catalog, no pages,
136
+ * or cannot be read at all.
137
+ */
138
+ declare function mergePdfs(sources: readonly BinaryContent[]): Promise<Uint8Array>;
139
+
140
+ /**
141
+ * A PDF holding some of another's pages.
142
+ *
143
+ * Selection writes a fresh document, not an incremental update: an update
144
+ * keeps the original bytes, so every dropped page, its content and its fields
145
+ * would still be in the file. The new document holds the catalog, a new page
146
+ * tree over the kept pages, and every object those reach. Dropped pages, the
147
+ * widgets that sit only on them, and form fields left with no widget are not
148
+ * carried; a reference to one from what is kept is dropped from a list and
149
+ * becomes `null` anywhere else.
150
+ */
151
+
152
+ /** Return a PDF containing the requested one-based pages in source order. */
153
+ declare function selectPdfPages(template: BinaryContent, requestedPages: readonly number[]): Promise<Uint8Array>;
154
+
155
+ interface PdfOverlayBase {
156
+ /** One-based page number. */
157
+ page: number;
158
+ /** Horizontal position in PDF points from the bottom-left corner. */
159
+ x: number;
160
+ /** Vertical position in PDF points from the bottom-left corner. */
161
+ y: number;
162
+ }
163
+ type PdfTextOverlay = PdfOverlayBase & {
164
+ fontSize?: number;
165
+ /**
166
+ * Fit text inside this width, shrinking no smaller than 6 points. Text that
167
+ * still does not fit fails with an overflow error.
168
+ */
169
+ width?: number;
170
+ /** Vertically center text inside this height. */
171
+ height?: number;
172
+ /** RGB components in the range 0–1. */
173
+ color?: [number, number, number];
174
+ /**
175
+ * A font for this overlay alone, tried before the render's other fonts, so
176
+ * one render can draw text in more than one font (a bold heading, say).
177
+ */
178
+ font?: PdfFont;
179
+ } & ({
180
+ text: string | number | boolean;
181
+ field?: never;
182
+ } | {
183
+ field: string;
184
+ text?: never;
185
+ });
186
+ type PdfImageOverlay = PdfOverlayBase & {
187
+ image: Uint8Array;
188
+ mediaType: 'image/png' | 'image/jpeg';
189
+ width: number;
190
+ height: number;
191
+ fit?: 'contain' | 'fill';
192
+ };
193
+ type PdfOverlay = PdfTextOverlay | PdfImageOverlay;
194
+
195
+ interface RenderPdfOptions {
196
+ template: BinaryContent;
197
+ form?: Form;
198
+ data: Record<string, unknown>;
199
+ bindings?: Record<string, string>;
200
+ formatter?: Formatter;
201
+ overlays?: PdfOverlay[];
202
+ /**
203
+ * A font supplied at render time. It is tried first for every text value,
204
+ * ahead of the layer's declared font.
205
+ */
206
+ font?: PdfFont;
207
+ /** The font the artifact's PDF layer declares, tried after `font`. */
208
+ layerFont?: PdfFont;
209
+ /**
210
+ * The presentation the artifact's PDF layer declares, applied over
211
+ * `formatter`. `{ money: { currencyDisplay: 'none' } }` prints amounts
212
+ * without a symbol beside a template's pre-printed one.
213
+ */
214
+ format?: LayerFormat;
215
+ }
216
+ declare function renderPdf({ template, form, data, bindings, formatter, overlays, font, layerFont, format, }: RenderPdfOptions): Promise<BinaryContent>;
217
+
218
+ /**
219
+ * PDF signature fields: the file structure a digital signature lives in.
220
+ *
221
+ * A signature is an incremental update (ISO 32000-1, 12.8). The update adds a
222
+ * signature dictionary, a signature field whose widget sits on the first page
223
+ * and whose `/V` is that dictionary, and an AcroForm entry with `/SigFlags 3`.
224
+ * The dictionary's `/ByteRange` covers the whole file except the `/Contents`
225
+ * hex string, which holds the signature container.
226
+ *
227
+ * This module writes and reads that structure only. Producing and checking the
228
+ * container (CMS, keys, certificates) is the caller's work: prepare the field,
229
+ * sign the bytes its byte range covers, then embed the container.
230
+ */
231
+ /** What a new signature dictionary says about the signature. */
232
+ interface PdfSignatureOptions {
233
+ /** Bytes reserved for the signature container. The embedded container may be shorter, never longer. */
234
+ contentsSize: number;
235
+ /** The signing time, written as `/M`. */
236
+ signingTime: Date;
237
+ /** The signer's name, in any script (`/Name`). */
238
+ name?: string;
239
+ /** Why the document was signed (`/Reason`). */
240
+ reason?: string;
241
+ /** Where it was signed (`/Location`). */
242
+ location?: string;
243
+ /** How to reach the signer (`/ContactInfo`). */
244
+ contactInfo?: string;
245
+ }
246
+ /** A PDF with a signature field whose container is still empty. */
247
+ interface PreparedPdfSignature {
248
+ /** The PDF, with `/ByteRange` written and `/Contents` zero-filled. */
249
+ bytes: Uint8Array;
250
+ /** `[0, gapStart, gapEnd, length - gapEnd]`: the two ranges the signature covers. */
251
+ byteRange: [number, number, number, number];
252
+ }
253
+ /** The newest signature in a PDF, read from its signature dictionary. */
254
+ interface PdfSignatureRecord {
255
+ /** The signature container, including any zero padding after it. */
256
+ contents: Uint8Array;
257
+ /** The ranges the signature covers, as the dictionary states them. */
258
+ byteRange: [number, number, number, number];
259
+ /** The bytes `byteRange` covers, concatenated. */
260
+ signedBytes: Uint8Array;
261
+ /**
262
+ * True when the byte range starts at the first byte, ends at the last byte,
263
+ * and leaves out exactly this dictionary's `/Contents` hex string. False when
264
+ * any other byte is unsigned, such as an update appended after signing.
265
+ */
266
+ coversWholeFile: boolean;
267
+ name?: string;
268
+ reason?: string;
269
+ location?: string;
270
+ contactInfo?: string;
271
+ signingTime?: Date;
272
+ }
273
+ /**
274
+ * `pdf` with a new, empty signature field added as an incremental update.
275
+ *
276
+ * The field is invisible (a zero-size widget on the first page). Its byte range
277
+ * is final; sign `signedBytes(prepared)` and pass the container to
278
+ * `embedPdfSignature`.
279
+ */
280
+ declare function preparePdfSignature(pdf: Uint8Array, options: PdfSignatureOptions): Promise<PreparedPdfSignature>;
281
+ /** The bytes a prepared signature covers: what the signature container signs. */
282
+ declare function signedBytes(prepared: PreparedPdfSignature): Uint8Array;
283
+ /** The prepared PDF with `container` written into its `/Contents`. */
284
+ declare function embedPdfSignature(prepared: PreparedPdfSignature, container: Uint8Array): Uint8Array;
285
+ /**
286
+ * The newest signature in `pdf`: the signature dictionary whose byte range
287
+ * reaches furthest into the file. Every value comes from that dictionary, so
288
+ * other objects (an annotation's `/Contents`, a field's `/Name`) never stand in
289
+ * for it. Returns `undefined` when the file holds no signature.
290
+ */
291
+ declare function readPdfSignature(pdf: Uint8Array): Promise<PdfSignatureRecord | undefined>;
292
+
293
+ interface PdfRendererOptions {
294
+ formatter?: Formatter;
295
+ /**
296
+ * A font supplied at render time, such as a licensed corporate font. It is
297
+ * tried before the font the layer declares.
298
+ */
299
+ font?: PdfFont;
300
+ }
301
+ type PdfLayer = RendererLayer & {
302
+ type: 'pdf';
303
+ content: Uint8Array;
304
+ };
305
+ declare function pdfRenderer(options?: PdfRendererOptions): AsterdocRenderer<PdfLayer, Uint8Array>;
306
+
307
+ declare const FieldType: {
308
+ readonly SIGNATURE: 0;
309
+ readonly INITIALS: 1;
310
+ };
311
+ type FieldTypeValue = (typeof FieldType)[keyof typeof FieldType];
312
+ declare function encode(signerIndex: number, fieldType: number): string;
313
+ interface DecodedEncoding {
314
+ signerIndex: number;
315
+ fieldType: number;
316
+ }
317
+ interface DecodedEncodingWithPosition extends DecodedEncoding {
318
+ /** Character position in the scanned text where the encoding starts. */
319
+ position: number;
320
+ }
321
+ declare function decodeAll(text: string): DecodedEncodingWithPosition[];
322
+ declare function stripEncoding(text: string): string;
323
+ declare function containsEncoding(text: string): boolean;
324
+
325
+ /** One text-showing run, in content-stream order. */
326
+ interface TextRun {
327
+ /** Decoded Unicode text of the run. */
328
+ text: string;
329
+ /** Device-space x of the run start, in points. */
330
+ x: number;
331
+ /** Device-space y of the run start (bottom-origin), in points. */
332
+ y: number;
333
+ /** Advance width of the run in device space, in points. */
334
+ width: number;
335
+ /** Effective font height in device space, in points. */
336
+ height: number;
337
+ }
338
+
339
+ /** A signature or initials field located in the PDF. */
340
+ interface ExtractedField {
341
+ signerIndex: number;
342
+ fieldType: 'signature' | 'initials';
343
+ /** 1-based page number. */
344
+ page: number;
345
+ /** Points from the left page edge. */
346
+ x: number;
347
+ /** Points from the top page edge. */
348
+ y: number;
349
+ width: number;
350
+ height: number;
351
+ /** Raw bottom-origin y from the PDF. */
352
+ rawY: number;
353
+ pageHeight: number;
354
+ }
355
+ /** A decoded marker whose field type code has no meaning to this reader. */
356
+ interface UnknownMarker {
357
+ /** 1-based page number. */
358
+ page: number;
359
+ signerIndex: number;
360
+ /** The raw field type code (0-15). */
361
+ fieldType: number;
362
+ }
363
+ /**
364
+ * Thrown when a PDF carries markers whose field type is not signature or
365
+ * initials. Such a marker comes from a newer encoder or a damaged text layer;
366
+ * reading it as either known type could put a signer's mark in the wrong box.
367
+ */
368
+ declare class UnknownMarkerError extends Error {
369
+ readonly markers: UnknownMarker[];
370
+ constructor(markers: UnknownMarker[]);
371
+ }
372
+ /**
373
+ * Extract signature/initials fields from a PDF produced by a converter.
374
+ *
375
+ * @throws {UnknownMarkerError} naming every marker whose field type is not
376
+ * signature or initials.
377
+ */
378
+ declare function extractFieldsFromPdf(pdf: Uint8Array): Promise<ExtractedField[]>;
379
+ /** Positioned, merged text runs for one page, with its geometry. */
380
+ interface PageTextRuns {
381
+ /** [x0, y0, x1, y1] MediaBox in points. */
382
+ mediaBox: [number, number, number, number];
383
+ runs: TextRun[];
384
+ }
385
+ /**
386
+ * Merged text runs for every page, in document order. Low-level building
387
+ * block for verification and layout tooling; coordinates are raw PDF user
388
+ * space (bottom-origin y).
389
+ */
390
+ declare function pageTextRuns(pdf: Uint8Array): Promise<PageTextRuns[]>;
391
+ /** True when any page's text layer contains encoding characters. */
392
+ declare function pdfContainsEncoding(pdf: Uint8Array): Promise<boolean>;
393
+
394
+ /**
395
+ * A placement query against a converter-produced PDF.
396
+ *
397
+ * - `marker`: find the invisible encoding for a signer index + field type
398
+ * that the render stage injected into the document.
399
+ * - `anchor`: find literal document text. Without `occurrence` the text must
400
+ * appear exactly once; ambiguity is an error, not a guess.
401
+ */
402
+ type LocateQuery = {
403
+ id: string;
404
+ } & ({
405
+ kind: 'marker';
406
+ signerIndex: number;
407
+ fieldType: FieldTypeValue;
408
+ } | {
409
+ kind: 'anchor';
410
+ text: string;
411
+ occurrence?: number;
412
+ });
413
+
414
+ /**
415
+ * Factory returning a locator object for core's `seal({ locate })` option.
416
+ * Kept as a factory so future variants (imported-PDF tier, hosted tier) share
417
+ * the calling convention.
418
+ */
419
+ declare function locator(): {
420
+ locate: typeof locate;
421
+ };
422
+ /** Thrown when any query cannot be resolved deterministically. */
423
+ declare class LocateError extends Error {
424
+ readonly failures: {
425
+ id: string;
426
+ reason: 'missing' | 'ambiguous';
427
+ matches?: number;
428
+ }[];
429
+ constructor(message: string, failures: {
430
+ id: string;
431
+ reason: 'missing' | 'ambiguous';
432
+ matches?: number;
433
+ }[]);
434
+ }
435
+ /**
436
+ * Resolve placement queries against a PDF. All queries succeed or the call
437
+ * throws a `LocateError` naming every failed id — partial results are never
438
+ * returned, so a seal pipeline cannot proceed on a silently incomplete map.
439
+ */
440
+ declare function locate(pdf: Uint8Array, queries: LocateQuery[]): Promise<LocateHit[]>;
441
+
442
+ /** Why a PDF could not be read as the artifact's filled form. */
443
+ type PdfExtractionErrorCode = 'malformed_pdf' | 'no_form_fields' | 'not_matching' | 'no_pdf_layer' | 'layer_required' | 'layer_not_found' | 'not_pdf_layer' | 'unknown_bindings_source';
444
+ /** Extraction refused the input. `code` says which failure case applies. */
445
+ declare class PdfExtractionError extends Error {
446
+ readonly code: PdfExtractionErrorCode;
447
+ constructor(code: PdfExtractionErrorCode, message: string);
448
+ }
449
+ /** What happened to one artifact path the layer's bindings target. */
450
+ type PdfExtractionStatus = 'recovered' | 'empty' | 'not_recoverable' | 'unparseable';
451
+ /** One PDF field that carries a binding target, with the raw value read from it. */
452
+ interface PdfExtractionSource {
453
+ /** Fully qualified AcroForm field name. */
454
+ field: string;
455
+ /** Raw PDF value: the text, the selected option, or a button state name. Absent when the field has none. */
456
+ value?: string;
457
+ }
458
+ /** One entry per artifact path the layer's bindings target. */
459
+ interface PdfExtractionEntry {
460
+ /** The binding target, as written in the layer's bindings. */
461
+ path: string;
462
+ status: PdfExtractionStatus;
463
+ /** Every PDF field that carries this path. */
464
+ sources: PdfExtractionSource[];
465
+ /** Why the value is not recoverable or could not be parsed. */
466
+ reason?: string;
467
+ }
468
+ /** A PDF field that holds a value no binding covers. */
469
+ interface PdfUnboundField {
470
+ field: string;
471
+ type: 'text' | 'checkbox' | 'radio' | 'dropdown';
472
+ value: string;
473
+ }
474
+ interface PdfExtractionReport {
475
+ entries: PdfExtractionEntry[];
476
+ unbound: PdfUnboundField[];
477
+ }
478
+ /** Partial artifact data in the fill payload shape. It holds only values recovered exactly. */
479
+ interface PdfExtractedData {
480
+ fields: Record<string, unknown>;
481
+ parties?: Record<string, unknown>;
482
+ annexes?: Record<string, unknown>;
483
+ }
484
+ interface PdfExtraction {
485
+ data: PdfExtractedData;
486
+ report: PdfExtractionReport;
487
+ }
488
+ interface ExtractPdfDataOptions {
489
+ /** The filled PDF. It is read, never modified. */
490
+ pdf: BinaryContent;
491
+ /** The artifact whose layer produced the PDF. */
492
+ form: Form;
493
+ /** The PDF layer's bindings: AcroForm field name to artifact path. */
494
+ bindings: Record<string, string>;
495
+ /** The formatter the PDF was filled with. Defaults to the default formatter. */
496
+ formatter?: Formatter;
497
+ /**
498
+ * The presentation the PDF layer declares, applied over `formatter` as it
499
+ * was when filling. With `money.currencyDisplay: 'none'`, an amount is read
500
+ * in the currency its field declares.
501
+ */
502
+ format?: LayerFormat;
503
+ }
504
+ /**
505
+ * Read a filled PDF back into artifact data through the layer's bindings.
506
+ *
507
+ * Only exact reversals are returned: direct fields, split fields, checkbox and
508
+ * radio maps. A joined binding's raw text is reported as not recoverable, and
509
+ * text that does not parse into the field's type is reported with its raw
510
+ * value. Nothing is validated here; pass the data to the normal fill path.
511
+ *
512
+ * @throws {PdfEncryptedError} when the PDF is encrypted.
513
+ * @throws {PdfExtractionError} when the PDF or the layer choice cannot be read.
514
+ */
515
+ declare function extractPdfData({ pdf, form, bindings, formatter: filledWith, format }: ExtractPdfDataOptions): Promise<PdfExtraction>;
516
+ /** A PDF layer as the artifact declares it. */
517
+ interface PdfLayerSpec {
518
+ mimeType?: string;
519
+ bindings?: Record<string, string>;
520
+ bindingsFrom?: string;
521
+ format?: LayerFormat;
522
+ }
523
+ /**
524
+ * Choose the PDF layer to read against: the named one, or the only PDF layer.
525
+ * Returns its key, resolved bindings, and declared format.
526
+ */
527
+ declare function selectPdfExtractionLayer(layers: Record<string, PdfLayerSpec> | undefined, requested?: string): {
528
+ key: string;
529
+ bindings: Record<string, string>;
530
+ format?: LayerFormat;
531
+ };
532
+
533
+ /**
534
+ * Authoring check that the values an artifact can bind to a PDF form's text
535
+ * fields fit their boxes.
536
+ *
537
+ * Filling fails when a value cannot fit its box at {@link MIN_FONT_SIZE}, or
538
+ * has more characters than a comb field has boxes. This check finds those
539
+ * failures before any data exists: for each binding to an AcroForm text field
540
+ * it builds values the bound artifact field accepts and lays them out with the
541
+ * same code filling uses.
542
+ *
543
+ * A text, email, uuid, or uri field is checked at its length bound: `maxLength`
544
+ * characters, or the length its `pattern` bounds (a uuid without a pattern
545
+ * takes its 36-character canonical form). Two values of that length are laid out:
546
+ * - a typical value: each open position holds the next character of
547
+ * {@link TYPICAL_TEXT}; a position the pattern constrains holds the allowed
548
+ * character nearest the allowed characters' mean width. When it cannot fit,
549
+ * ordinary answers fail to fill: an error.
550
+ * - the widest value: each position holds the widest character it may hold
551
+ * (the widest Latin letter or digit when open, `W` in Helvetica). When only
552
+ * this value cannot fit, unusual answers fail to fill: a warning.
553
+ *
554
+ * A split binding (`path:2`) takes the matching hyphen-separated part of the
555
+ * pattern, or the whole value's bound when the pattern does not fix the parts.
556
+ * Enum and multiselect fields write known option values, so they are checked
557
+ * exactly: the widest option value, or the widest `max` values (all of them
558
+ * without `max`) joined with ", ". A comma-joined binding joins each path's
559
+ * value with ", ". More characters than a comb field has boxes is an error.
560
+ *
561
+ * The font is the one filling would choose: the layer's declared font, then
562
+ * the form's own font for the field, then Helvetica. A font supplied only at
563
+ * render time is not known here.
564
+ */
565
+
566
+ /**
567
+ * The text a typical value is made of: an English pangram with its word spaces,
568
+ * repeated. It holds every lowercase letter, one capital, and spaces at about
569
+ * the rate English prose has them, so its mean advance (456 units in Helvetica)
570
+ * sits just above that of letter-frequency-weighted English text (441).
571
+ */
572
+ declare const TYPICAL_TEXT = "The quick brown fox jumps over the lazy dog ";
573
+ /** Why a binding may not fit its PDF text field. */
574
+ type PdfBindingFitReason = 'overflow' | 'comb-length' | 'unbounded';
575
+ /** One binding whose values may not fit the PDF text field it fills. */
576
+ interface PdfBindingFitIssue {
577
+ /** Fully qualified name of the PDF form field. */
578
+ field: string;
579
+ /** The binding as the layer declares it. */
580
+ binding: string;
581
+ /** The artifact paths the binding reads, such as `fields.amountSource`. */
582
+ paths: string[];
583
+ /**
584
+ * `error` when a typical value, an option value, or a value's length cannot
585
+ * be filled; `warning` when only the widest value overflows, or nothing
586
+ * bounds the value.
587
+ */
588
+ severity: 'error' | 'warning';
589
+ reason: PdfBindingFitReason;
590
+ /** Which value failed: a typical one, or the widest. Absent for `unbounded`. */
591
+ value?: 'typical' | 'widest';
592
+ /** For `overflow`, the minimum font size in points; for `comb-length`, the number of comb boxes. */
593
+ limit?: number;
594
+ /** Characters in the widest value checked. */
595
+ length?: number;
596
+ message: string;
597
+ }
598
+ /** Options for {@link checkPdfBindingFit}. */
599
+ interface CheckPdfBindingFitOptions {
600
+ /** The PDF layer's bytes. */
601
+ template: Uint8Array;
602
+ form: Form;
603
+ /** The layer's bindings; without them, fields fill the PDF fields of the same name. */
604
+ bindings?: Record<string, string>;
605
+ /** The font the layer declares. */
606
+ layerFont?: PdfFont;
607
+ }
608
+ /**
609
+ * Check that every value the artifact accepts for a binding to a PDF text
610
+ * field can be filled: that it fits the box at the minimum font size, and
611
+ * that it has no more characters than a comb field has boxes. A text field
612
+ * with nothing bounding its length is a warning. A PDF without an AcroForm
613
+ * has nothing to check.
614
+ *
615
+ * @throws {PdfFontError} when the layer's font cannot be read.
616
+ * @throws {PdfBindingSyntaxError} when a binding cannot be parsed.
617
+ */
618
+ declare function checkPdfBindingFit({ template, form, bindings, layerFont }: CheckPdfBindingFitOptions): Promise<PdfBindingFitIssue[]>;
619
+
620
+ export { type CheckPdfBindingFitOptions, type DecodedEncoding, type DecodedEncodingWithPosition, type ExtractPdfDataOptions, type ExtractedField, FieldType, type FieldTypeValue, type InspectOptions, LocateError, type LocateQuery, MIN_FONT_SIZE, type PageTextRuns, type PdfBindingFitIssue, type PdfBindingFitReason, PdfEncryptedError, type PdfExtractedData, type PdfExtraction, type PdfExtractionEntry, PdfExtractionError, type PdfExtractionErrorCode, type PdfExtractionReport, type PdfExtractionSource, type PdfExtractionStatus, type PdfFieldFillDetail, PdfFieldFillError, type PdfFieldFillReason, type PdfFieldInfo, type PdfFieldType, PdfFont, type PdfImageOverlay, type PdfInfo, PdfMergeError, type PdfOverlay, type PdfPageInfo, type PdfRendererOptions, type PdfSignatureOptions, type PdfSignatureRecord, type PdfTextOverlay, type PdfUnboundField, type PreparedPdfSignature, type RenderPdfOptions, TYPICAL_TEXT, type TextRun, type UnknownMarker, UnknownMarkerError, checkPdfBindingFit, containsEncoding, decodeAll, embedPdfSignature, encode, extractFieldsFromPdf, extractPdfData, flattenPdf, inspectAcroFormFields, inspectPdf, locate, locator, mergePdfs, pageTextRuns, pdfContainsEncoding, pdfRenderer, preparePdfSignature, readPdfSignature, renderPdf, selectPdfExtractionLayer, selectPdfPages, signedBytes, stripEncoding };