pdf-lite 1.3.3 → 1.4.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/acroform/PdfAcroForm.d.ts +63 -0
- package/dist/acroform/PdfAcroForm.js +279 -0
- package/dist/acroform/PdfFontEncodingCache.d.ts +16 -0
- package/dist/acroform/PdfFontEncodingCache.js +75 -0
- package/dist/acroform/acroform.d.ts +7 -454
- package/dist/acroform/acroform.js +5 -1664
- package/dist/acroform/appearance/PdfAppearanceStream.d.ts +15 -0
- package/dist/acroform/appearance/PdfAppearanceStream.js +32 -0
- package/dist/acroform/appearance/PdfButtonAppearanceStream.d.ts +12 -0
- package/dist/acroform/appearance/PdfButtonAppearanceStream.js +54 -0
- package/dist/acroform/appearance/PdfChoiceAppearanceStream.d.ts +15 -0
- package/dist/acroform/appearance/PdfChoiceAppearanceStream.js +48 -0
- package/dist/acroform/appearance/PdfTextAppearanceStream.d.ts +17 -0
- package/dist/acroform/appearance/PdfTextAppearanceStream.js +75 -0
- package/dist/acroform/appearance/index.d.ts +4 -0
- package/dist/acroform/appearance/index.js +4 -0
- package/dist/acroform/fields/PdfButtonFormField.d.ts +9 -0
- package/dist/acroform/fields/PdfButtonFormField.js +35 -0
- package/dist/acroform/fields/PdfChoiceFormField.d.ts +9 -0
- package/dist/acroform/fields/PdfChoiceFormField.js +46 -0
- package/dist/acroform/fields/PdfDefaultAppearance.d.ts +23 -0
- package/dist/acroform/fields/PdfDefaultAppearance.js +68 -0
- package/dist/acroform/fields/PdfFormField.d.ts +119 -0
- package/dist/acroform/fields/PdfFormField.js +499 -0
- package/dist/acroform/fields/PdfFormFieldFlags.d.ts +46 -0
- package/dist/acroform/fields/PdfFormFieldFlags.js +128 -0
- package/dist/acroform/fields/PdfSignatureFormField.d.ts +7 -0
- package/dist/acroform/fields/PdfSignatureFormField.js +12 -0
- package/dist/acroform/fields/PdfTextFormField.d.ts +10 -0
- package/dist/acroform/fields/PdfTextFormField.js +52 -0
- package/dist/acroform/fields/index.d.ts +8 -0
- package/dist/acroform/fields/index.js +8 -0
- package/dist/acroform/fields/types.d.ts +21 -0
- package/dist/acroform/fields/types.js +9 -0
- package/dist/acroform/index.d.ts +5 -1
- package/dist/acroform/index.js +5 -1
- package/dist/acroform/manager.d.ts +7 -0
- package/dist/acroform/manager.js +12 -0
- package/dist/acroform/xfa/PdfXfaData.d.ts +20 -0
- package/dist/acroform/xfa/PdfXfaData.js +68 -0
- package/dist/acroform/xfa/PdfXfaForm.d.ts +12 -0
- package/dist/acroform/xfa/PdfXfaForm.js +64 -0
- package/dist/acroform/xfa/index.d.ts +3 -0
- package/dist/acroform/xfa/index.js +2 -0
- package/dist/annotations/PdfAnnotation.d.ts +40 -0
- package/dist/annotations/PdfAnnotation.js +105 -0
- package/dist/annotations/PdfAnnotationFlags.d.ts +25 -0
- package/dist/annotations/PdfAnnotationFlags.js +94 -0
- package/dist/annotations/PdfAnnotationWriter.d.ts +20 -0
- package/dist/annotations/PdfAnnotationWriter.js +76 -0
- package/dist/annotations/PdfWidgetAnnotation.d.ts +15 -0
- package/dist/annotations/PdfWidgetAnnotation.js +37 -0
- package/dist/annotations/index.d.ts +4 -0
- package/dist/annotations/index.js +4 -0
- package/dist/core/objects/pdf-array.d.ts +1 -1
- package/dist/core/objects/pdf-array.js +3 -2
- package/dist/core/objects/pdf-boolean.d.ts +1 -1
- package/dist/core/objects/pdf-boolean.js +3 -2
- package/dist/core/objects/pdf-comment.d.ts +1 -1
- package/dist/core/objects/pdf-comment.js +1 -1
- package/dist/core/objects/pdf-dictionary.d.ts +1 -1
- package/dist/core/objects/pdf-dictionary.js +3 -2
- package/dist/core/objects/pdf-hexadecimal.d.ts +1 -1
- package/dist/core/objects/pdf-hexadecimal.js +3 -2
- package/dist/core/objects/pdf-indirect-object.d.ts +1 -1
- package/dist/core/objects/pdf-indirect-object.js +1 -1
- package/dist/core/objects/pdf-name.d.ts +1 -1
- package/dist/core/objects/pdf-name.js +3 -2
- package/dist/core/objects/pdf-null.d.ts +1 -1
- package/dist/core/objects/pdf-null.js +3 -2
- package/dist/core/objects/pdf-number.d.ts +1 -1
- package/dist/core/objects/pdf-number.js +3 -2
- package/dist/core/objects/pdf-object-reference.d.ts +1 -1
- package/dist/core/objects/pdf-object-reference.js +3 -2
- package/dist/core/objects/pdf-object.d.ts +3 -1
- package/dist/core/objects/pdf-object.js +6 -0
- package/dist/core/objects/pdf-start-xref.d.ts +1 -1
- package/dist/core/objects/pdf-start-xref.js +3 -2
- package/dist/core/objects/pdf-stream.d.ts +3 -3
- package/dist/core/objects/pdf-stream.js +39 -14
- package/dist/core/objects/pdf-string.d.ts +2 -1
- package/dist/core/objects/pdf-string.js +17 -2
- package/dist/core/objects/pdf-trailer.d.ts +1 -1
- package/dist/core/objects/pdf-trailer.js +3 -2
- package/dist/core/objects/pdf-xref-table.d.ts +3 -3
- package/dist/core/objects/pdf-xref-table.js +3 -3
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/pdf/pdf-document.d.ts +14 -11
- package/dist/pdf/pdf-document.js +36 -26
- package/dist/pdf/pdf-revision.d.ts +1 -1
- package/dist/pdf/pdf-revision.js +1 -1
- package/dist/pdf/pdf-xref-lookup.d.ts +8 -0
- package/dist/pdf/pdf-xref-lookup.js +12 -0
- package/dist/security/handlers/base.js +3 -0
- package/package.json +1 -1
- package/dist/xfa/index.d.ts +0 -1
- package/dist/xfa/index.js +0 -1
- package/dist/xfa/manager.d.ts +0 -44
- package/dist/xfa/manager.js +0 -136
package/dist/index.js
CHANGED
|
@@ -12,7 +12,6 @@ import { PdfTrailerEntries } from '../core/objects/pdf-trailer.js';
|
|
|
12
12
|
import { PdfDocumentSecurityStoreObject } from '../signing/document-security-store.js';
|
|
13
13
|
import { ByteArray } from '../types.js';
|
|
14
14
|
import { PdfDocumentVerificationResult, PdfSigner } from '../signing/signer.js';
|
|
15
|
-
import { PdfXfaManager } from '../xfa/manager.js';
|
|
16
15
|
import { PdfAcroFormManager } from '../acroform/manager.js';
|
|
17
16
|
import { PdfFontManager } from '../fonts/font-manager.js';
|
|
18
17
|
/**
|
|
@@ -39,9 +38,9 @@ export declare class PdfDocument extends PdfObject {
|
|
|
39
38
|
signer: PdfSigner;
|
|
40
39
|
/** Security handler for encryption/decryption operations */
|
|
41
40
|
securityHandler?: PdfSecurityHandler;
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
41
|
+
/** */
|
|
42
|
+
readonly acroForm: PdfAcroFormManager;
|
|
43
|
+
readonly fonts: PdfFontManager;
|
|
45
44
|
private hasEncryptionDictionary?;
|
|
46
45
|
private toBeCommitted;
|
|
47
46
|
/**
|
|
@@ -65,12 +64,6 @@ export declare class PdfDocument extends PdfObject {
|
|
|
65
64
|
});
|
|
66
65
|
get header(): PdfComment | undefined;
|
|
67
66
|
set header(comment: PdfComment | undefined);
|
|
68
|
-
/** XFA manager for handling XFA forms */
|
|
69
|
-
get xfa(): PdfXfaManager;
|
|
70
|
-
/** AcroForm manager for handling form fields */
|
|
71
|
-
get acroForm(): PdfAcroFormManager;
|
|
72
|
-
/** Font manager for embedding and managing fonts */
|
|
73
|
-
get fonts(): PdfFontManager;
|
|
74
67
|
/**
|
|
75
68
|
* Creates a PdfDocument from an array of PDF objects.
|
|
76
69
|
* Parses objects into revisions based on EOF comments.
|
|
@@ -93,6 +86,16 @@ export declare class PdfDocument extends PdfObject {
|
|
|
93
86
|
* @param objects - PDF objects to add to the document
|
|
94
87
|
*/
|
|
95
88
|
add(...objects: PdfObject[]): void;
|
|
89
|
+
/**
|
|
90
|
+
* Packs non-stream indirect objects into compressed ObjStm containers.
|
|
91
|
+
* Objects that already have an object number are left unchanged.
|
|
92
|
+
* Appearance streams and other PdfStream objects must NOT be passed here —
|
|
93
|
+
* only non-stream indirect objects (dictionaries, arrays, etc.) are eligible.
|
|
94
|
+
*
|
|
95
|
+
* @param objects - Non-stream indirect objects to compress into ObjStm
|
|
96
|
+
* @param batchSize - Maximum objects per ObjStm container (default 100)
|
|
97
|
+
*/
|
|
98
|
+
addObjectsAsStream(objects: PdfIndirectObject[], batchSize?: number): void;
|
|
96
99
|
/**
|
|
97
100
|
* Gets the latest (most recent) revision of the document.
|
|
98
101
|
*
|
|
@@ -284,7 +287,7 @@ export declare class PdfDocument extends PdfObject {
|
|
|
284
287
|
*
|
|
285
288
|
* @returns A cloned PdfDocument instance
|
|
286
289
|
*/
|
|
287
|
-
|
|
290
|
+
cloneImpl(): this;
|
|
288
291
|
/**
|
|
289
292
|
* Creates a PdfDocument from a byte stream.
|
|
290
293
|
*
|
package/dist/pdf/pdf-document.js
CHANGED
|
@@ -17,7 +17,6 @@ import { PdfStartXRef } from '../core/objects/pdf-start-xref.js';
|
|
|
17
17
|
import { FoundCompressedObjectError } from './errors.js';
|
|
18
18
|
import { PdfReader } from './pdf-reader.js';
|
|
19
19
|
import { PdfSigner } from '../signing/signer.js';
|
|
20
|
-
import { PdfXfaManager } from '../xfa/manager.js';
|
|
21
20
|
import { PdfAcroFormManager } from '../acroform/manager.js';
|
|
22
21
|
import { PdfFontManager } from '../fonts/font-manager.js';
|
|
23
22
|
import { concatUint8Arrays } from '../utils/concatUint8Arrays.js';
|
|
@@ -45,9 +44,9 @@ export class PdfDocument extends PdfObject {
|
|
|
45
44
|
signer;
|
|
46
45
|
/** Security handler for encryption/decryption operations */
|
|
47
46
|
securityHandler;
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
47
|
+
/** */
|
|
48
|
+
acroForm;
|
|
49
|
+
fonts;
|
|
51
50
|
hasEncryptionDictionary = false;
|
|
52
51
|
toBeCommitted = [];
|
|
53
52
|
/**
|
|
@@ -81,6 +80,8 @@ export class PdfDocument extends PdfObject {
|
|
|
81
80
|
this.calculateOffsets();
|
|
82
81
|
this.securityHandler =
|
|
83
82
|
options?.securityHandler ?? this.getSecurityHandler();
|
|
83
|
+
this.acroForm = new PdfAcroFormManager(this);
|
|
84
|
+
this.fonts = new PdfFontManager(this);
|
|
84
85
|
}
|
|
85
86
|
get header() {
|
|
86
87
|
return this.revisions[0].header;
|
|
@@ -89,27 +90,6 @@ export class PdfDocument extends PdfObject {
|
|
|
89
90
|
if (comment)
|
|
90
91
|
this.revisions[0].header = comment;
|
|
91
92
|
}
|
|
92
|
-
/** XFA manager for handling XFA forms */
|
|
93
|
-
get xfa() {
|
|
94
|
-
if (!this._xfa) {
|
|
95
|
-
this._xfa = new PdfXfaManager(this);
|
|
96
|
-
}
|
|
97
|
-
return this._xfa;
|
|
98
|
-
}
|
|
99
|
-
/** AcroForm manager for handling form fields */
|
|
100
|
-
get acroForm() {
|
|
101
|
-
if (!this._acroForm) {
|
|
102
|
-
this._acroForm = new PdfAcroFormManager(this);
|
|
103
|
-
}
|
|
104
|
-
return this._acroForm;
|
|
105
|
-
}
|
|
106
|
-
/** Font manager for embedding and managing fonts */
|
|
107
|
-
get fonts() {
|
|
108
|
-
if (!this._fonts) {
|
|
109
|
-
this._fonts = new PdfFontManager(this);
|
|
110
|
-
}
|
|
111
|
-
return this._fonts;
|
|
112
|
-
}
|
|
113
93
|
/**
|
|
114
94
|
* Creates a PdfDocument from an array of PDF objects.
|
|
115
95
|
* Parses objects into revisions based on EOF comments.
|
|
@@ -170,6 +150,36 @@ export class PdfDocument extends PdfObject {
|
|
|
170
150
|
this.latestRevision.addObject(obj);
|
|
171
151
|
}
|
|
172
152
|
}
|
|
153
|
+
/**
|
|
154
|
+
* Packs non-stream indirect objects into compressed ObjStm containers.
|
|
155
|
+
* Objects that already have an object number are left unchanged.
|
|
156
|
+
* Appearance streams and other PdfStream objects must NOT be passed here —
|
|
157
|
+
* only non-stream indirect objects (dictionaries, arrays, etc.) are eligible.
|
|
158
|
+
*
|
|
159
|
+
* @param objects - Non-stream indirect objects to compress into ObjStm
|
|
160
|
+
* @param batchSize - Maximum objects per ObjStm container (default 100)
|
|
161
|
+
*/
|
|
162
|
+
addObjectsAsStream(objects, batchSize = 100) {
|
|
163
|
+
if (objects.length === 0)
|
|
164
|
+
return;
|
|
165
|
+
for (let start = 0; start < objects.length; start += batchSize) {
|
|
166
|
+
const batch = objects.slice(start, Math.min(start + batchSize, objects.length));
|
|
167
|
+
// Pre-assign a contiguous block of object numbers for the batch
|
|
168
|
+
const xref = this.latestRevision.xref;
|
|
169
|
+
const startNum = xref.reserveObjectNumbers(batch.length);
|
|
170
|
+
for (let i = 0; i < batch.length; i++) {
|
|
171
|
+
if (!batch[i].inPdf()) {
|
|
172
|
+
batch[i].objectNumber = startNum + i;
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
// Build the ObjStm and apply FlateDecode compression
|
|
176
|
+
const objStream = PdfObjStream.fromObjects(batch);
|
|
177
|
+
objStream.addFilter('FlateDecode');
|
|
178
|
+
// Add the container — xref.addObject() auto-registers children as type-2 entries
|
|
179
|
+
const container = new PdfIndirectObject({ content: objStream });
|
|
180
|
+
this.add(container);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
173
183
|
/**
|
|
174
184
|
* Gets the latest (most recent) revision of the document.
|
|
175
185
|
*
|
|
@@ -729,7 +739,7 @@ export class PdfDocument extends PdfObject {
|
|
|
729
739
|
*
|
|
730
740
|
* @returns A cloned PdfDocument instance
|
|
731
741
|
*/
|
|
732
|
-
|
|
742
|
+
cloneImpl() {
|
|
733
743
|
const clonedRevisions = this.revisions.map((rev) => rev.clone());
|
|
734
744
|
return new PdfDocument({
|
|
735
745
|
revisions: clonedRevisions,
|
package/dist/pdf/pdf-revision.js
CHANGED
|
@@ -250,7 +250,7 @@ export class PdfRevision extends PdfObject {
|
|
|
250
250
|
*
|
|
251
251
|
* @returns A cloned PdfRevision instance
|
|
252
252
|
*/
|
|
253
|
-
|
|
253
|
+
cloneImpl() {
|
|
254
254
|
const clonedObjects = this.objects.map((obj) => obj.clone());
|
|
255
255
|
return new PdfRevision({ objects: clonedObjects });
|
|
256
256
|
}
|
|
@@ -110,6 +110,14 @@ export declare class PdfXrefLookup {
|
|
|
110
110
|
* @returns The updated xref object
|
|
111
111
|
*/
|
|
112
112
|
update(): PdfIndirectObject<PdfXRefStream> | PdfXRefTable;
|
|
113
|
+
/**
|
|
114
|
+
* Reserves a contiguous block of object numbers without registering objects.
|
|
115
|
+
* Use this to pre-assign numbers to objects that will live inside an ObjStm.
|
|
116
|
+
*
|
|
117
|
+
* @param count - Number of object numbers to reserve
|
|
118
|
+
* @returns The first reserved object number
|
|
119
|
+
*/
|
|
120
|
+
reserveObjectNumbers(count: number): number;
|
|
113
121
|
/**
|
|
114
122
|
* Adds an indirect object to the xref lookup.
|
|
115
123
|
* Assigns an object number if not already set.
|
|
@@ -305,6 +305,18 @@ export class PdfXrefLookup {
|
|
|
305
305
|
this.object = newObject;
|
|
306
306
|
return this.object;
|
|
307
307
|
}
|
|
308
|
+
/**
|
|
309
|
+
* Reserves a contiguous block of object numbers without registering objects.
|
|
310
|
+
* Use this to pre-assign numbers to objects that will live inside an ObjStm.
|
|
311
|
+
*
|
|
312
|
+
* @param count - Number of object numbers to reserve
|
|
313
|
+
* @returns The first reserved object number
|
|
314
|
+
*/
|
|
315
|
+
reserveObjectNumbers(count) {
|
|
316
|
+
const startNum = this.size;
|
|
317
|
+
this.size += count;
|
|
318
|
+
return startNum;
|
|
319
|
+
}
|
|
308
320
|
/**
|
|
309
321
|
* Adds an indirect object to the xref lookup.
|
|
310
322
|
* Assigns an object number if not already set.
|
|
@@ -87,11 +87,14 @@ export class PdfSecurityHandler {
|
|
|
87
87
|
else if (obj instanceof PdfString) {
|
|
88
88
|
const decryptedData = await this.decrypt('string', obj.raw, objectNumber, generationNumber);
|
|
89
89
|
obj.raw = decryptedData;
|
|
90
|
+
obj.setModified(false);
|
|
90
91
|
}
|
|
91
92
|
else if (obj instanceof PdfStream) {
|
|
92
93
|
const decryptedData = await this.decrypt('stream', obj.raw, objectNumber, generationNumber);
|
|
93
94
|
obj.raw = decryptedData;
|
|
94
95
|
await decryptObject(obj.header);
|
|
96
|
+
obj.setModified(false);
|
|
97
|
+
obj.header.setModified(false);
|
|
95
98
|
}
|
|
96
99
|
else if (obj instanceof PdfDictionary) {
|
|
97
100
|
const values = obj.values;
|
package/package.json
CHANGED
package/dist/xfa/index.d.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { PdfXfaManager } from './manager.js';
|
package/dist/xfa/index.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { PdfXfaManager } from './manager.js';
|
package/dist/xfa/manager.d.ts
DELETED
|
@@ -1,44 +0,0 @@
|
|
|
1
|
-
import { PdfDocument } from '../pdf/pdf-document.js';
|
|
2
|
-
/**
|
|
3
|
-
* Manages XFA (XML Forms Architecture) forms in PDF documents.
|
|
4
|
-
* Provides methods to read and write XFA form data as XML.
|
|
5
|
-
*/
|
|
6
|
-
export declare class PdfXfaManager {
|
|
7
|
-
private document;
|
|
8
|
-
private _datasetsStream?;
|
|
9
|
-
constructor(document: PdfDocument);
|
|
10
|
-
/**
|
|
11
|
-
* Checks if the document contains XFA forms.
|
|
12
|
-
* @returns True if the document has XFA forms, false otherwise
|
|
13
|
-
*/
|
|
14
|
-
hasXfaForms(): Promise<boolean>;
|
|
15
|
-
/**
|
|
16
|
-
* Reads the XFA form data as XML string.
|
|
17
|
-
* @returns The XFA datasets XML content, or null if no XFA form exists
|
|
18
|
-
*/
|
|
19
|
-
readXml(): Promise<string | null>;
|
|
20
|
-
/**
|
|
21
|
-
* Writes XML content to the XFA datasets stream.
|
|
22
|
-
* @param xml The XML content to write
|
|
23
|
-
* @throws Error if the document doesn't have XFA forms
|
|
24
|
-
*/
|
|
25
|
-
writeXml(xml: string): Promise<void>;
|
|
26
|
-
/**
|
|
27
|
-
* Gets the AcroForm dictionary from the document catalog.
|
|
28
|
-
* @returns The AcroForm dictionary or null if not found
|
|
29
|
-
*/
|
|
30
|
-
private getAcroForm;
|
|
31
|
-
/**
|
|
32
|
-
* Gets the XFA datasets stream.
|
|
33
|
-
* Caches the stream for subsequent calls to preserve modifications.
|
|
34
|
-
* @returns The datasets stream or null if not found
|
|
35
|
-
*/
|
|
36
|
-
private getDatasetsStream;
|
|
37
|
-
/**
|
|
38
|
-
* Finds the XFA dataset object reference from the XFA array.
|
|
39
|
-
* XFA array structure: [(name1) ref1 (name2) ref2 ...]
|
|
40
|
-
* @param xfaArray The XFA array from the AcroForm
|
|
41
|
-
* @returns The object reference to the datasets stream, or null if not found
|
|
42
|
-
*/
|
|
43
|
-
private findXfaDatasetReference;
|
|
44
|
-
}
|
package/dist/xfa/manager.js
DELETED
|
@@ -1,136 +0,0 @@
|
|
|
1
|
-
import { PdfStream } from '../core/objects/pdf-stream.js';
|
|
2
|
-
import { PdfDictionary } from '../core/objects/pdf-dictionary.js';
|
|
3
|
-
import { PdfArray } from '../core/objects/pdf-array.js';
|
|
4
|
-
import { PdfString } from '../core/objects/pdf-string.js';
|
|
5
|
-
import { PdfObjectReference } from '../core/objects/pdf-object-reference.js';
|
|
6
|
-
import { PdfIndirectObject } from '../core/index.js';
|
|
7
|
-
/**
|
|
8
|
-
* Manages XFA (XML Forms Architecture) forms in PDF documents.
|
|
9
|
-
* Provides methods to read and write XFA form data as XML.
|
|
10
|
-
*/
|
|
11
|
-
export class PdfXfaManager {
|
|
12
|
-
document;
|
|
13
|
-
_datasetsStream;
|
|
14
|
-
constructor(document) {
|
|
15
|
-
this.document = document;
|
|
16
|
-
}
|
|
17
|
-
/**
|
|
18
|
-
* Checks if the document contains XFA forms.
|
|
19
|
-
* @returns True if the document has XFA forms, false otherwise
|
|
20
|
-
*/
|
|
21
|
-
async hasXfaForms() {
|
|
22
|
-
try {
|
|
23
|
-
const stream = await this.getDatasetsStream();
|
|
24
|
-
return stream !== null;
|
|
25
|
-
}
|
|
26
|
-
catch {
|
|
27
|
-
return false;
|
|
28
|
-
}
|
|
29
|
-
}
|
|
30
|
-
/**
|
|
31
|
-
* Reads the XFA form data as XML string.
|
|
32
|
-
* @returns The XFA datasets XML content, or null if no XFA form exists
|
|
33
|
-
*/
|
|
34
|
-
async readXml() {
|
|
35
|
-
const stream = await this.getDatasetsStream();
|
|
36
|
-
if (!stream)
|
|
37
|
-
return null;
|
|
38
|
-
// Get decompressed data without modifying the original stream
|
|
39
|
-
const decompressed = stream.content.decode();
|
|
40
|
-
// Return the raw XML content as string
|
|
41
|
-
const decoder = new TextDecoder();
|
|
42
|
-
return decoder.decode(decompressed);
|
|
43
|
-
}
|
|
44
|
-
/**
|
|
45
|
-
* Writes XML content to the XFA datasets stream.
|
|
46
|
-
* @param xml The XML content to write
|
|
47
|
-
* @throws Error if the document doesn't have XFA forms
|
|
48
|
-
*/
|
|
49
|
-
async writeXml(xml) {
|
|
50
|
-
const stream = await this.getDatasetsStream();
|
|
51
|
-
if (!stream) {
|
|
52
|
-
throw new Error('Document does not contain XFA forms');
|
|
53
|
-
}
|
|
54
|
-
// Update the cached stream directly with the new XML content
|
|
55
|
-
const datasetsIndirect = new PdfIndirectObject({
|
|
56
|
-
...stream,
|
|
57
|
-
content: PdfStream.fromString(xml),
|
|
58
|
-
});
|
|
59
|
-
const isIncremental = this.document.isIncremental();
|
|
60
|
-
this.document.setIncremental(true);
|
|
61
|
-
await this.document.commit(datasetsIndirect);
|
|
62
|
-
this.document.setIncremental(isIncremental);
|
|
63
|
-
// Reset cached stream to force re-fetch if needed
|
|
64
|
-
this._datasetsStream = undefined;
|
|
65
|
-
}
|
|
66
|
-
/**
|
|
67
|
-
* Gets the AcroForm dictionary from the document catalog.
|
|
68
|
-
* @returns The AcroForm dictionary or null if not found
|
|
69
|
-
*/
|
|
70
|
-
async getAcroForm() {
|
|
71
|
-
const catalog = this.document.root;
|
|
72
|
-
const acroFormRef = catalog.content.get('AcroForm');
|
|
73
|
-
if (!acroFormRef)
|
|
74
|
-
return null;
|
|
75
|
-
if (acroFormRef instanceof PdfObjectReference) {
|
|
76
|
-
const acroFormObject = await this.document.readObject({
|
|
77
|
-
objectNumber: acroFormRef.objectNumber,
|
|
78
|
-
generationNumber: acroFormRef.generationNumber,
|
|
79
|
-
});
|
|
80
|
-
if (!acroFormObject)
|
|
81
|
-
return null;
|
|
82
|
-
return acroFormObject.content.as(PdfDictionary);
|
|
83
|
-
}
|
|
84
|
-
else if (acroFormRef instanceof PdfDictionary) {
|
|
85
|
-
return acroFormRef;
|
|
86
|
-
}
|
|
87
|
-
return null;
|
|
88
|
-
}
|
|
89
|
-
/**
|
|
90
|
-
* Gets the XFA datasets stream.
|
|
91
|
-
* Caches the stream for subsequent calls to preserve modifications.
|
|
92
|
-
* @returns The datasets stream or null if not found
|
|
93
|
-
*/
|
|
94
|
-
async getDatasetsStream() {
|
|
95
|
-
if (this._datasetsStream) {
|
|
96
|
-
return this._datasetsStream;
|
|
97
|
-
}
|
|
98
|
-
const acroForm = await this.getAcroForm();
|
|
99
|
-
if (!acroForm)
|
|
100
|
-
return null;
|
|
101
|
-
const xfaArray = acroForm.get('XFA');
|
|
102
|
-
if (!(xfaArray instanceof PdfArray))
|
|
103
|
-
return null;
|
|
104
|
-
const datasetsRef = this.findXfaDatasetReference(xfaArray);
|
|
105
|
-
if (!datasetsRef)
|
|
106
|
-
return null;
|
|
107
|
-
const datasetObject = await this.document.readObject({
|
|
108
|
-
objectNumber: datasetsRef.objectNumber,
|
|
109
|
-
generationNumber: datasetsRef.generationNumber,
|
|
110
|
-
allowUnindexed: true,
|
|
111
|
-
});
|
|
112
|
-
if (!datasetObject)
|
|
113
|
-
return null;
|
|
114
|
-
return datasetObject;
|
|
115
|
-
}
|
|
116
|
-
/**
|
|
117
|
-
* Finds the XFA dataset object reference from the XFA array.
|
|
118
|
-
* XFA array structure: [(name1) ref1 (name2) ref2 ...]
|
|
119
|
-
* @param xfaArray The XFA array from the AcroForm
|
|
120
|
-
* @returns The object reference to the datasets stream, or null if not found
|
|
121
|
-
*/
|
|
122
|
-
findXfaDatasetReference(xfaArray) {
|
|
123
|
-
const items = xfaArray.items;
|
|
124
|
-
// XFA array alternates between name strings and object references
|
|
125
|
-
for (let i = 0; i < items.length - 1; i += 2) {
|
|
126
|
-
const name = items[i];
|
|
127
|
-
const ref = items[i + 1];
|
|
128
|
-
if (name instanceof PdfString && name.value === 'datasets') {
|
|
129
|
-
if (ref instanceof PdfObjectReference) {
|
|
130
|
-
return ref;
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
}
|
|
134
|
-
return null;
|
|
135
|
-
}
|
|
136
|
-
}
|