wpd-codec 3.2.2 → 3.3.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/README.md CHANGED
@@ -71,7 +71,7 @@ readWpdContent(bytes, {
71
71
  });
72
72
  ```
73
73
 
74
- Structural nonconformance is not a diagnostic — it throws. `WpdNotAWordPerfectFileError`, `WpdEncryptedDocumentError`, `WpdUnsupportedVersionError`, and the general `WpdFormatError` are all exported, and all extend the last.
74
+ Structural nonconformance is not a diagnostic — it throws. `WpdNotAWordPerfectFileError`, `WpdEncryptedDocumentError`, `WpdWrongPasswordError`, `WpdUnsupportedVersionError`, and the general `WpdFormatError` are all exported, and all extend the last.
75
75
 
76
76
  ## What it provides
77
77
 
@@ -179,7 +179,7 @@ Everything below is recognised by the tokeniser and skipped by the fold, so a do
179
179
  - **Embedded OLE objects**, stored under the compound file's `PerfectOffice_OBJECTS` storage and named by an image box's Graphics Filename packet's own `0x70`/`0x71` (OLE Object Descriptor / OLE Object Data) children. `archive-codec`'s compound-file reader already reaches that storage, which is how `ooxml.js` recovers a ZIP-payload embedded object — but a WordPerfect OLE object's payload is a native OLE server's own stream rather than a nested document package (`ooxml.js`'s own equivalent case, a classic OLE1 `.bin` payload with no `Package` stream, stays opaque by the identical scope boundary), so recovering one generically is a project in its own right, not a wiring job.
180
180
  - **The counter groups** (0xD8, 0xD9, 0xDB, 0xDC): setting, numbering-method, increment and decrement carry no text and change no structure this reader models, so only the Display Number group's own paragraph-number pair is read.
181
181
  - **Every merge subfunction other than FIELD** (ASSIGN, CALL, IF, FOR, CASE, and the rest of WordPerfect's own merge scripting language) and **cross-references** (0xD5). A cross-reference's displayed text survives as ordinary text; its target binding does not. Reported through `wpd/merge-code-dropped` and `wpd/cross-reference-flattened`. Unlike FIELD, these can legitimately wrap whole paragraphs of body text as control flow, which the run-scoped field construct's own one-paragraph extent cannot express regardless — a schema gap for a scripting language's control flow, not a parsing gap.
182
- - **Encrypted documents**, which throw: the specification states that nothing beyond the file header is intelligible without the password, so there is no partial read to offer.
182
+ - **WordPerfect 9-and-later "enhanced encryption"**, which throws: a different, unpublished cipher whose header word is not the standard mode's password checksum, so a `password` read option either verifies against that checksum and decrypts the standard ("original") mode or throws `WpdWrongPasswordError` naming both possible readings of the mismatch. The standard mode itself is decrypted for real (see `src/container/encryption.ts` for the cipher's two independent sources, and for the honest limit that no open-source reference implementation of the 6.x wiring exists to cross-check against a WordPerfect-produced encrypted file).
183
183
 
184
184
  ## Evidence
185
185
 
@@ -1,6 +1,7 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  const require_errors = require("../errors.cjs");
3
3
  const require_container_header = require("./header.cjs");
4
+ const require_container_encryption = require("./encryption.cjs");
4
5
  const require_container_prefix = require("./prefix.cjs");
5
6
  let archive_codec = require("archive-codec");
6
7
  //#region src/container/container.ts
@@ -35,9 +36,11 @@ function documentAreaEnd(bytes, header) {
35
36
  if (fileSize > documentAreaOffset && fileSize <= bytes.length) return fileSize;
36
37
  return bytes.length;
37
38
  }
38
- function openWpdDocument(input) {
39
- const { bytes, compound } = unwrapContainer(toArrayBufferBacked(input));
40
- const header = require_container_header.readFileHeader(bytes);
39
+ function openWpdDocument(input, options = {}) {
40
+ const { bytes: wrapped, compound } = unwrapContainer(toArrayBufferBacked(input));
41
+ const header = require_container_header.readFileHeader(wrapped, options);
42
+ const suppliedPassword = options.password === "" ? void 0 : options.password;
43
+ const bytes = header.encryption !== 0 && suppliedPassword !== void 0 ? require_container_encryption.decryptWpdDocument(wrapped, header, suppliedPassword) : wrapped;
41
44
  return {
42
45
  header,
43
46
  packets: require_container_prefix.readPrefixPackets(bytes, header),
@@ -1,4 +1,4 @@
1
- import { WpdFileHeader } from "./header.cjs";
1
+ import { ReadWpdHeaderOptions, WpdFileHeader } from "./header.cjs";
2
2
  import { WpdPrefixPacket } from "./prefix.cjs";
3
3
  //#region src/container/container.d.ts
4
4
  declare const PERFECT_OFFICE_MAIN_STREAM = "PerfectOffice_MAIN";
@@ -11,6 +11,6 @@ interface WpdDocumentContainer {
11
11
  readonly documentAreaEnd: number;
12
12
  readonly compound: boolean;
13
13
  }
14
- declare function openWpdDocument(input: Uint8Array): WpdDocumentContainer;
14
+ declare function openWpdDocument(input: Uint8Array, options?: ReadWpdHeaderOptions): WpdDocumentContainer;
15
15
  //#endregion
16
16
  export { PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, WpdDocumentContainer, openWpdDocument };
@@ -1,4 +1,4 @@
1
- import { WpdFileHeader } from "./header.js";
1
+ import { ReadWpdHeaderOptions, WpdFileHeader } from "./header.js";
2
2
  import { WpdPrefixPacket } from "./prefix.js";
3
3
  //#region src/container/container.d.ts
4
4
  declare const PERFECT_OFFICE_MAIN_STREAM = "PerfectOffice_MAIN";
@@ -11,6 +11,6 @@ interface WpdDocumentContainer {
11
11
  readonly documentAreaEnd: number;
12
12
  readonly compound: boolean;
13
13
  }
14
- declare function openWpdDocument(input: Uint8Array): WpdDocumentContainer;
14
+ declare function openWpdDocument(input: Uint8Array, options?: ReadWpdHeaderOptions): WpdDocumentContainer;
15
15
  //#endregion
16
16
  export { PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, WpdDocumentContainer, openWpdDocument };
@@ -1,5 +1,6 @@
1
1
  import { WpdNotAWordPerfectFileError } from "../errors.js";
2
2
  import { hasWordPerfectFileId, readFileHeader } from "./header.js";
3
+ import { decryptWpdDocument } from "./encryption.js";
3
4
  import { readPrefixPackets } from "./prefix.js";
4
5
  import { isCompoundFile, readCompoundFile } from "archive-codec";
5
6
  //#region src/container/container.ts
@@ -34,9 +35,11 @@ function documentAreaEnd(bytes, header) {
34
35
  if (fileSize > documentAreaOffset && fileSize <= bytes.length) return fileSize;
35
36
  return bytes.length;
36
37
  }
37
- function openWpdDocument(input) {
38
- const { bytes, compound } = unwrapContainer(toArrayBufferBacked(input));
39
- const header = readFileHeader(bytes);
38
+ function openWpdDocument(input, options = {}) {
39
+ const { bytes: wrapped, compound } = unwrapContainer(toArrayBufferBacked(input));
40
+ const header = readFileHeader(wrapped, options);
41
+ const suppliedPassword = options.password === "" ? void 0 : options.password;
42
+ const bytes = header.encryption !== 0 && suppliedPassword !== void 0 ? decryptWpdDocument(wrapped, header, suppliedPassword) : wrapped;
40
43
  return {
41
44
  header,
42
45
  packets: readPrefixPackets(bytes, header),
@@ -0,0 +1,59 @@
1
+ Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
+ const require_errors = require("../errors.cjs");
3
+ const require_bytes_view = require("../bytes/view.cjs");
4
+ require("./header.cjs");
5
+ //#region src/container/encryption.ts
6
+ function normaliseWpdPassword(password) {
7
+ const normalised = [];
8
+ for (let i = 0; i < password.length; i++) {
9
+ const unit = password.charCodeAt(i);
10
+ if (unit > 255) throw new require_errors.WpdFormatError(`A password with characters outside Latin-1 cannot be encoded into the byte-keyed WordPerfect cipher (code unit U+${unit.toString(16).toUpperCase().padStart(4, "0")} at position ${i}).`);
11
+ normalised.push(unit >= 97 && unit <= 122 ? unit - 97 + 65 : unit);
12
+ }
13
+ return normalised;
14
+ }
15
+ function wpdPasswordChecksum16(normalised) {
16
+ let checksum = 0;
17
+ for (const unit of normalised) {
18
+ checksum = (checksum >>> 1 | checksum << 15) ^ unit << 8;
19
+ checksum &= 65535;
20
+ }
21
+ return checksum;
22
+ }
23
+ function applyWpdStandardEncryption(bytes, normalised, startOffset) {
24
+ if (normalised.length === 0) throw new require_errors.WpdFormatError("The WordPerfect cipher is keyed by the password's own bytes, so an empty password decrypts nothing.");
25
+ const maskBase = normalised.length + 1 & 255;
26
+ const output = new Uint8Array(bytes.length);
27
+ output.set(bytes.subarray(0, startOffset));
28
+ for (let pos = startOffset; pos < bytes.length; pos++) {
29
+ const relative = pos - startOffset;
30
+ const passwordByte = normalised[relative % normalised.length];
31
+ if (passwordByte === void 0) throw new require_errors.WpdFormatError("The password normalised to no bytes, which the cipher cannot key with.");
32
+ const mask = maskBase + relative & 255;
33
+ output[pos] = require_bytes_view.byteAt(bytes, pos) ^ passwordByte ^ mask;
34
+ }
35
+ return output;
36
+ }
37
+ function decryptWpdDocument(bytes, header, password) {
38
+ const normalised = normaliseWpdPassword(password);
39
+ if (normalised.length === 0) throw new require_errors.WpdWrongPasswordError(header.encryption, 0);
40
+ const checksum = wpdPasswordChecksum16(normalised);
41
+ if (checksum !== header.encryption) throw new require_errors.WpdWrongPasswordError(header.encryption, checksum);
42
+ return applyWpdStandardEncryption(bytes, normalised, 512);
43
+ }
44
+ function encryptWpdDocumentForTests(bytes, password) {
45
+ const normalised = normaliseWpdPassword(password);
46
+ const checksum = wpdPasswordChecksum16(normalised);
47
+ const encrypted = applyWpdStandardEncryption(bytes, normalised, 512);
48
+ const output = new Uint8Array(encrypted.length);
49
+ output.set(encrypted);
50
+ output[12] = checksum & 255;
51
+ output[13] = checksum >>> 8 & 255;
52
+ return output;
53
+ }
54
+ //#endregion
55
+ exports.applyWpdStandardEncryption = applyWpdStandardEncryption;
56
+ exports.decryptWpdDocument = decryptWpdDocument;
57
+ exports.encryptWpdDocumentForTests = encryptWpdDocumentForTests;
58
+ exports.normaliseWpdPassword = normaliseWpdPassword;
59
+ exports.wpdPasswordChecksum16 = wpdPasswordChecksum16;
@@ -0,0 +1,9 @@
1
+ import { WpdFileHeader } from "./header.cjs";
2
+ //#region src/container/encryption.d.ts
3
+ declare function normaliseWpdPassword(password: string): number[];
4
+ declare function wpdPasswordChecksum16(normalised: readonly number[]): number;
5
+ declare function applyWpdStandardEncryption(bytes: Uint8Array, normalised: readonly number[], startOffset: number): Uint8Array<ArrayBuffer>;
6
+ declare function decryptWpdDocument(bytes: Uint8Array<ArrayBuffer>, header: WpdFileHeader, password: string): Uint8Array<ArrayBuffer>;
7
+ declare function encryptWpdDocumentForTests(bytes: Uint8Array, password: string): Uint8Array<ArrayBuffer>;
8
+ //#endregion
9
+ export { applyWpdStandardEncryption, decryptWpdDocument, encryptWpdDocumentForTests, normaliseWpdPassword, wpdPasswordChecksum16 };
@@ -0,0 +1,9 @@
1
+ import { WpdFileHeader } from "./header.js";
2
+ //#region src/container/encryption.d.ts
3
+ declare function normaliseWpdPassword(password: string): number[];
4
+ declare function wpdPasswordChecksum16(normalised: readonly number[]): number;
5
+ declare function applyWpdStandardEncryption(bytes: Uint8Array, normalised: readonly number[], startOffset: number): Uint8Array<ArrayBuffer>;
6
+ declare function decryptWpdDocument(bytes: Uint8Array<ArrayBuffer>, header: WpdFileHeader, password: string): Uint8Array<ArrayBuffer>;
7
+ declare function encryptWpdDocumentForTests(bytes: Uint8Array, password: string): Uint8Array<ArrayBuffer>;
8
+ //#endregion
9
+ export { applyWpdStandardEncryption, decryptWpdDocument, encryptWpdDocumentForTests, normaliseWpdPassword, wpdPasswordChecksum16 };
@@ -0,0 +1,54 @@
1
+ import { WpdFormatError, WpdWrongPasswordError } from "../errors.js";
2
+ import { byteAt } from "../bytes/view.js";
3
+ import "./header.js";
4
+ //#region src/container/encryption.ts
5
+ function normaliseWpdPassword(password) {
6
+ const normalised = [];
7
+ for (let i = 0; i < password.length; i++) {
8
+ const unit = password.charCodeAt(i);
9
+ if (unit > 255) throw new WpdFormatError(`A password with characters outside Latin-1 cannot be encoded into the byte-keyed WordPerfect cipher (code unit U+${unit.toString(16).toUpperCase().padStart(4, "0")} at position ${i}).`);
10
+ normalised.push(unit >= 97 && unit <= 122 ? unit - 97 + 65 : unit);
11
+ }
12
+ return normalised;
13
+ }
14
+ function wpdPasswordChecksum16(normalised) {
15
+ let checksum = 0;
16
+ for (const unit of normalised) {
17
+ checksum = (checksum >>> 1 | checksum << 15) ^ unit << 8;
18
+ checksum &= 65535;
19
+ }
20
+ return checksum;
21
+ }
22
+ function applyWpdStandardEncryption(bytes, normalised, startOffset) {
23
+ if (normalised.length === 0) throw new WpdFormatError("The WordPerfect cipher is keyed by the password's own bytes, so an empty password decrypts nothing.");
24
+ const maskBase = normalised.length + 1 & 255;
25
+ const output = new Uint8Array(bytes.length);
26
+ output.set(bytes.subarray(0, startOffset));
27
+ for (let pos = startOffset; pos < bytes.length; pos++) {
28
+ const relative = pos - startOffset;
29
+ const passwordByte = normalised[relative % normalised.length];
30
+ if (passwordByte === void 0) throw new WpdFormatError("The password normalised to no bytes, which the cipher cannot key with.");
31
+ const mask = maskBase + relative & 255;
32
+ output[pos] = byteAt(bytes, pos) ^ passwordByte ^ mask;
33
+ }
34
+ return output;
35
+ }
36
+ function decryptWpdDocument(bytes, header, password) {
37
+ const normalised = normaliseWpdPassword(password);
38
+ if (normalised.length === 0) throw new WpdWrongPasswordError(header.encryption, 0);
39
+ const checksum = wpdPasswordChecksum16(normalised);
40
+ if (checksum !== header.encryption) throw new WpdWrongPasswordError(header.encryption, checksum);
41
+ return applyWpdStandardEncryption(bytes, normalised, 512);
42
+ }
43
+ function encryptWpdDocumentForTests(bytes, password) {
44
+ const normalised = normaliseWpdPassword(password);
45
+ const checksum = wpdPasswordChecksum16(normalised);
46
+ const encrypted = applyWpdStandardEncryption(bytes, normalised, 512);
47
+ const output = new Uint8Array(encrypted.length);
48
+ output.set(encrypted);
49
+ output[12] = checksum & 255;
50
+ output[13] = checksum >>> 8 & 255;
51
+ return output;
52
+ }
53
+ //#endregion
54
+ export { applyWpdStandardEncryption, decryptWpdDocument, encryptWpdDocumentForTests, normaliseWpdPassword, wpdPasswordChecksum16 };
@@ -16,7 +16,7 @@ function hasWordPerfectFileId(bytes) {
16
16
  if (bytes.length < WPD_FILE_ID.length) return false;
17
17
  return WPD_FILE_ID.every((expected, index) => bytes[index] === expected);
18
18
  }
19
- function readFileHeader(bytes) {
19
+ function readFileHeader(bytes, options = {}) {
20
20
  if (!hasWordPerfectFileId(bytes)) {
21
21
  const actual = Array.from(require_bytes_view.sliceAt(bytes, 0, Math.min(4, bytes.length))).map((byte) => byte.toString(16).padStart(2, "0")).join(" ");
22
22
  throw new require_errors.WpdNotAWordPerfectFileError(`Expected the WordPerfect file ID FF 57 50 43 (-1,"WPC") at offset 0, found ${actual}.`);
@@ -28,7 +28,8 @@ function readFileHeader(bytes) {
28
28
  const minorVersion = require_bytes_view.byteAt(bytes, 11);
29
29
  const encryption = require_bytes_view.uint16At(bytes, 12);
30
30
  const indexAreaOffset = require_bytes_view.uint16At(bytes, 14);
31
- if (encryption !== 0) throw new require_errors.WpdEncryptedDocumentError(`This document is encrypted (encryption word ${encryption}); nothing beyond the file header is intelligible without the password, which this reader does not support.`);
31
+ const suppliedPassword = options.password === "" ? void 0 : options.password;
32
+ if (encryption !== 0 && suppliedPassword === void 0) throw new require_errors.WpdEncryptedDocumentError(`This document is encrypted (encryption word ${encryption}); nothing beyond the file header is intelligible without the password. Pass { password } to read it -- the standard ("original") encryption mode is supported, and a non-matching password throws WpdWrongPasswordError.`);
32
33
  if (productType !== PRODUCT_TYPE_WORDPERFECT) throw new require_errors.WpdUnsupportedVersionError(`Product type ${productType} is not WordPerfect (${PRODUCT_TYPE_WORDPERFECT}); this file was produced by a different Corel product.`);
33
34
  if (!DOCUMENT_FILE_TYPES.includes(fileType)) throw new require_errors.WpdUnsupportedVersionError(`File type ${fileType} is not a WordPerfect document (expected ${DOCUMENT_FILE_TYPES.join(" or ")}).`);
34
35
  if (majorVersion !== MAJOR_VERSION_WP6_THROUGH_X6) throw new require_errors.WpdUnsupportedVersionError(`Major version ${majorVersion} is outside the WordPerfect 6.x-X6 lineage (major version ${MAJOR_VERSION_WP6_THROUGH_X6}), the one generation this reader covers.`);
@@ -39,7 +40,8 @@ function readFileHeader(bytes) {
39
40
  majorVersion,
40
41
  minorVersion,
41
42
  indexAreaOffset,
42
- fileSize: require_bytes_view.uint32At(bytes, 20)
43
+ fileSize: require_bytes_view.uint32At(bytes, 20),
44
+ encryption
43
45
  };
44
46
  }
45
47
  //#endregion
@@ -1,6 +1,9 @@
1
1
  //#region src/container/header.d.ts
2
2
  declare const WPD_FILE_ID: readonly number[];
3
3
  declare const WPD_PREFIX_HEADER_SIZE = 512;
4
+ interface ReadWpdHeaderOptions {
5
+ readonly password?: string;
6
+ }
4
7
  interface WpdFileHeader {
5
8
  readonly documentAreaOffset: number;
6
9
  readonly productType: number;
@@ -9,8 +12,9 @@ interface WpdFileHeader {
9
12
  readonly minorVersion: number;
10
13
  readonly indexAreaOffset: number;
11
14
  readonly fileSize: number;
15
+ readonly encryption: number;
12
16
  }
13
17
  declare function hasWordPerfectFileId(bytes: Uint8Array): boolean;
14
- declare function readFileHeader(bytes: Uint8Array): WpdFileHeader;
18
+ declare function readFileHeader(bytes: Uint8Array, options?: ReadWpdHeaderOptions): WpdFileHeader;
15
19
  //#endregion
16
- export { WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileId, readFileHeader };
20
+ export { ReadWpdHeaderOptions, WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileId, readFileHeader };
@@ -1,6 +1,9 @@
1
1
  //#region src/container/header.d.ts
2
2
  declare const WPD_FILE_ID: readonly number[];
3
3
  declare const WPD_PREFIX_HEADER_SIZE = 512;
4
+ interface ReadWpdHeaderOptions {
5
+ readonly password?: string;
6
+ }
4
7
  interface WpdFileHeader {
5
8
  readonly documentAreaOffset: number;
6
9
  readonly productType: number;
@@ -9,8 +12,9 @@ interface WpdFileHeader {
9
12
  readonly minorVersion: number;
10
13
  readonly indexAreaOffset: number;
11
14
  readonly fileSize: number;
15
+ readonly encryption: number;
12
16
  }
13
17
  declare function hasWordPerfectFileId(bytes: Uint8Array): boolean;
14
- declare function readFileHeader(bytes: Uint8Array): WpdFileHeader;
18
+ declare function readFileHeader(bytes: Uint8Array, options?: ReadWpdHeaderOptions): WpdFileHeader;
15
19
  //#endregion
16
- export { WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileId, readFileHeader };
20
+ export { ReadWpdHeaderOptions, WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileId, readFileHeader };
@@ -15,7 +15,7 @@ function hasWordPerfectFileId(bytes) {
15
15
  if (bytes.length < WPD_FILE_ID.length) return false;
16
16
  return WPD_FILE_ID.every((expected, index) => bytes[index] === expected);
17
17
  }
18
- function readFileHeader(bytes) {
18
+ function readFileHeader(bytes, options = {}) {
19
19
  if (!hasWordPerfectFileId(bytes)) {
20
20
  const actual = Array.from(sliceAt(bytes, 0, Math.min(4, bytes.length))).map((byte) => byte.toString(16).padStart(2, "0")).join(" ");
21
21
  throw new WpdNotAWordPerfectFileError(`Expected the WordPerfect file ID FF 57 50 43 (-1,"WPC") at offset 0, found ${actual}.`);
@@ -27,7 +27,8 @@ function readFileHeader(bytes) {
27
27
  const minorVersion = byteAt(bytes, 11);
28
28
  const encryption = uint16At(bytes, 12);
29
29
  const indexAreaOffset = uint16At(bytes, 14);
30
- if (encryption !== 0) throw new WpdEncryptedDocumentError(`This document is encrypted (encryption word ${encryption}); nothing beyond the file header is intelligible without the password, which this reader does not support.`);
30
+ const suppliedPassword = options.password === "" ? void 0 : options.password;
31
+ if (encryption !== 0 && suppliedPassword === void 0) throw new WpdEncryptedDocumentError(`This document is encrypted (encryption word ${encryption}); nothing beyond the file header is intelligible without the password. Pass { password } to read it -- the standard ("original") encryption mode is supported, and a non-matching password throws WpdWrongPasswordError.`);
31
32
  if (productType !== PRODUCT_TYPE_WORDPERFECT) throw new WpdUnsupportedVersionError(`Product type ${productType} is not WordPerfect (${PRODUCT_TYPE_WORDPERFECT}); this file was produced by a different Corel product.`);
32
33
  if (!DOCUMENT_FILE_TYPES.includes(fileType)) throw new WpdUnsupportedVersionError(`File type ${fileType} is not a WordPerfect document (expected ${DOCUMENT_FILE_TYPES.join(" or ")}).`);
33
34
  if (majorVersion !== MAJOR_VERSION_WP6_THROUGH_X6) throw new WpdUnsupportedVersionError(`Major version ${majorVersion} is outside the WordPerfect 6.x-X6 lineage (major version ${MAJOR_VERSION_WP6_THROUGH_X6}), the one generation this reader covers.`);
@@ -38,7 +39,8 @@ function readFileHeader(bytes) {
38
39
  majorVersion,
39
40
  minorVersion,
40
41
  indexAreaOffset,
41
- fileSize: uint32At(bytes, 20)
42
+ fileSize: uint32At(bytes, 20),
43
+ encryption
42
44
  };
43
45
  }
44
46
  //#endregion
package/dist/errors.cjs CHANGED
@@ -18,6 +18,16 @@ var WpdEncryptedDocumentError = class extends WpdFormatError {
18
18
  this.name = "WpdEncryptedDocumentError";
19
19
  }
20
20
  };
21
+ var WpdWrongPasswordError = class extends WpdFormatError {
22
+ headerEncryptionWord;
23
+ passwordChecksum;
24
+ constructor(headerEncryptionWord, passwordChecksum) {
25
+ super(`The header's encryption word (0x${headerEncryptionWord.toString(16)}) does not match this password's checksum (0x${passwordChecksum.toString(16)}): either the password is wrong, or the file uses the enhanced encryption mode (WordPerfect 9 and later), which this reader does not support.`);
26
+ this.headerEncryptionWord = headerEncryptionWord;
27
+ this.passwordChecksum = passwordChecksum;
28
+ this.name = "WpdWrongPasswordError";
29
+ }
30
+ };
21
31
  var WpdUnsupportedVersionError = class extends WpdFormatError {
22
32
  constructor(message) {
23
33
  super(message);
@@ -29,3 +39,4 @@ exports.WpdEncryptedDocumentError = WpdEncryptedDocumentError;
29
39
  exports.WpdFormatError = WpdFormatError;
30
40
  exports.WpdNotAWordPerfectFileError = WpdNotAWordPerfectFileError;
31
41
  exports.WpdUnsupportedVersionError = WpdUnsupportedVersionError;
42
+ exports.WpdWrongPasswordError = WpdWrongPasswordError;
package/dist/errors.d.cts CHANGED
@@ -8,8 +8,13 @@ declare class WpdNotAWordPerfectFileError extends WpdFormatError {
8
8
  declare class WpdEncryptedDocumentError extends WpdFormatError {
9
9
  constructor(message: string);
10
10
  }
11
+ declare class WpdWrongPasswordError extends WpdFormatError {
12
+ readonly headerEncryptionWord: number;
13
+ readonly passwordChecksum: number;
14
+ constructor(headerEncryptionWord: number, passwordChecksum: number);
15
+ }
11
16
  declare class WpdUnsupportedVersionError extends WpdFormatError {
12
17
  constructor(message: string);
13
18
  }
14
19
  //#endregion
15
- export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError };
20
+ export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError };
package/dist/errors.d.ts CHANGED
@@ -8,8 +8,13 @@ declare class WpdNotAWordPerfectFileError extends WpdFormatError {
8
8
  declare class WpdEncryptedDocumentError extends WpdFormatError {
9
9
  constructor(message: string);
10
10
  }
11
+ declare class WpdWrongPasswordError extends WpdFormatError {
12
+ readonly headerEncryptionWord: number;
13
+ readonly passwordChecksum: number;
14
+ constructor(headerEncryptionWord: number, passwordChecksum: number);
15
+ }
11
16
  declare class WpdUnsupportedVersionError extends WpdFormatError {
12
17
  constructor(message: string);
13
18
  }
14
19
  //#endregion
15
- export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError };
20
+ export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError };
package/dist/errors.js CHANGED
@@ -17,6 +17,16 @@ var WpdEncryptedDocumentError = class extends WpdFormatError {
17
17
  this.name = "WpdEncryptedDocumentError";
18
18
  }
19
19
  };
20
+ var WpdWrongPasswordError = class extends WpdFormatError {
21
+ headerEncryptionWord;
22
+ passwordChecksum;
23
+ constructor(headerEncryptionWord, passwordChecksum) {
24
+ super(`The header's encryption word (0x${headerEncryptionWord.toString(16)}) does not match this password's checksum (0x${passwordChecksum.toString(16)}): either the password is wrong, or the file uses the enhanced encryption mode (WordPerfect 9 and later), which this reader does not support.`);
25
+ this.headerEncryptionWord = headerEncryptionWord;
26
+ this.passwordChecksum = passwordChecksum;
27
+ this.name = "WpdWrongPasswordError";
28
+ }
29
+ };
20
30
  var WpdUnsupportedVersionError = class extends WpdFormatError {
21
31
  constructor(message) {
22
32
  super(message);
@@ -24,4 +34,4 @@ var WpdUnsupportedVersionError = class extends WpdFormatError {
24
34
  }
25
35
  };
26
36
  //#endregion
27
- export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError };
37
+ export { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError };
package/dist/index.cjs CHANGED
@@ -67,6 +67,7 @@ exports.WpdEncryptedDocumentError = require_errors.WpdEncryptedDocumentError;
67
67
  exports.WpdFormatError = require_errors.WpdFormatError;
68
68
  exports.WpdNotAWordPerfectFileError = require_errors.WpdNotAWordPerfectFileError;
69
69
  exports.WpdUnsupportedVersionError = require_errors.WpdUnsupportedVersionError;
70
+ exports.WpdWrongPasswordError = require_errors.WpdWrongPasswordError;
70
71
  exports.decodeAttributeByte = require_stream_attributes.decodeAttributeByte;
71
72
  exports.decodeSingleByteCharacter = require_stream_characters.decodeSingleByteCharacter;
72
73
  exports.decodeWordString = require_stream_characters.decodeWordString;
package/dist/index.d.cts CHANGED
@@ -5,7 +5,7 @@ import { WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileI
5
5
  import { PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, WPD_INDEX_RECORD_SIZE, WpdPrefixPacket, packetByPrefixId, readPrefixPackets, readTypefaceName } from "./container/prefix.cjs";
6
6
  import { PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, WpdDocumentContainer, openWpdDocument } from "./container/container.cjs";
7
7
  import { PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, readDocumentSummary } from "./container/summary.cjs";
8
- import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError } from "./errors.cjs";
8
+ import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError } from "./errors.cjs";
9
9
  import { WPD_FILE_EXTENSION, WPD_MEDIA_TYPE } from "./format.cjs";
10
10
  import { FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, WpdCharacterToken, WpdFixedFunctionToken, WpdSingleByteFunctionToken, WpdToken, WpdVariableFunctionToken, tokeniseDocumentArea } from "./stream/tokenise.cjs";
11
11
  import { EOL_GROUP, FIRST_SINGLE_BYTE_EOL, LAST_SINGLE_BYTE_EOL, WpdEolMapping, eolMappingForSubfunction, isSingleByteEol, subfunctionForSingleByteEol } from "./stream/eol.cjs";
@@ -16,4 +16,4 @@ import { COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_
16
16
  import { TAB_GROUP, WpdTabEffect, tabEffectFor } from "./stream/tab.cjs";
17
17
  import { DISPLAY_NUMBER_GROUP, STYLE_GROUP, WpdStyleSemantics, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isStyleScopeCloser, isStyleScopeOpener, readDisplayNumberLevel, readSystemStyleNumber, styleSemanticsFor } from "./stream/style.cjs";
18
18
  import { CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, ROW_INFORMATION_SUBFUNCTION, WpdCellFill, WpdCellInformation, WpdCellSpanning, WpdEmbeddedSubfunction, WpdEmbeddedSubfunctions, WpdRowInformation, findEmbeddedSubfunction, readCellFill, readCellInformation, readCellSpanning, readEmbeddedSubfunctions, readRowInformation, readTableColumnWidthPt } from "./stream/table.cjs";
19
- export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, type ReadWpdOptions, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, type WpdAttributeCode, WpdBytesSchema, type WpdCellFill, type WpdCellInformation, type WpdCellSpanning, type WpdCharacterToken, type WpdDiagnostic, WpdDiagnosticCodes, type WpdDiagnosticSink, type WpdDocumentContainer, type WpdEmbeddedSubfunction, type WpdEmbeddedSubfunctions, WpdEncryptedDocumentError, type WpdEolMapping, type WpdFileHeader, type WpdFixedFunctionToken, WpdFormatError, WpdNotAWordPerfectFileError, type WpdPageForm, type WpdPrefixPacket, type WpdRowInformation, type WpdRunAttributes, type WpdSingleByteFunctionToken, type WpdStyleSemantics, type WpdTabEffect, type WpdToken, WpdUnsupportedVersionError, type WpdVariableFunctionToken, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
19
+ export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, type ReadWpdOptions, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, type WpdAttributeCode, WpdBytesSchema, type WpdCellFill, type WpdCellInformation, type WpdCellSpanning, type WpdCharacterToken, type WpdDiagnostic, WpdDiagnosticCodes, type WpdDiagnosticSink, type WpdDocumentContainer, type WpdEmbeddedSubfunction, type WpdEmbeddedSubfunctions, WpdEncryptedDocumentError, type WpdEolMapping, type WpdFileHeader, type WpdFixedFunctionToken, WpdFormatError, WpdNotAWordPerfectFileError, type WpdPageForm, type WpdPrefixPacket, type WpdRowInformation, type WpdRunAttributes, type WpdSingleByteFunctionToken, type WpdStyleSemantics, type WpdTabEffect, type WpdToken, WpdUnsupportedVersionError, type WpdVariableFunctionToken, WpdWrongPasswordError, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
package/dist/index.d.ts CHANGED
@@ -5,7 +5,7 @@ import { WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, WpdFileHeader, hasWordPerfectFileI
5
5
  import { PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, WPD_INDEX_RECORD_SIZE, WpdPrefixPacket, packetByPrefixId, readPrefixPackets, readTypefaceName } from "./container/prefix.js";
6
6
  import { PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, WpdDocumentContainer, openWpdDocument } from "./container/container.js";
7
7
  import { PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, readDocumentSummary } from "./container/summary.js";
8
- import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError } from "./errors.js";
8
+ import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError } from "./errors.js";
9
9
  import { WPD_FILE_EXTENSION, WPD_MEDIA_TYPE } from "./format.js";
10
10
  import { FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, WpdCharacterToken, WpdFixedFunctionToken, WpdSingleByteFunctionToken, WpdToken, WpdVariableFunctionToken, tokeniseDocumentArea } from "./stream/tokenise.js";
11
11
  import { EOL_GROUP, FIRST_SINGLE_BYTE_EOL, LAST_SINGLE_BYTE_EOL, WpdEolMapping, eolMappingForSubfunction, isSingleByteEol, subfunctionForSingleByteEol } from "./stream/eol.js";
@@ -16,4 +16,4 @@ import { COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_
16
16
  import { TAB_GROUP, WpdTabEffect, tabEffectFor } from "./stream/tab.js";
17
17
  import { DISPLAY_NUMBER_GROUP, STYLE_GROUP, WpdStyleSemantics, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isStyleScopeCloser, isStyleScopeOpener, readDisplayNumberLevel, readSystemStyleNumber, styleSemanticsFor } from "./stream/style.js";
18
18
  import { CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, ROW_INFORMATION_SUBFUNCTION, WpdCellFill, WpdCellInformation, WpdCellSpanning, WpdEmbeddedSubfunction, WpdEmbeddedSubfunctions, WpdRowInformation, findEmbeddedSubfunction, readCellFill, readCellInformation, readCellSpanning, readEmbeddedSubfunctions, readRowInformation, readTableColumnWidthPt } from "./stream/table.js";
19
- export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, type ReadWpdOptions, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, type WpdAttributeCode, WpdBytesSchema, type WpdCellFill, type WpdCellInformation, type WpdCellSpanning, type WpdCharacterToken, type WpdDiagnostic, WpdDiagnosticCodes, type WpdDiagnosticSink, type WpdDocumentContainer, type WpdEmbeddedSubfunction, type WpdEmbeddedSubfunctions, WpdEncryptedDocumentError, type WpdEolMapping, type WpdFileHeader, type WpdFixedFunctionToken, WpdFormatError, WpdNotAWordPerfectFileError, type WpdPageForm, type WpdPrefixPacket, type WpdRowInformation, type WpdRunAttributes, type WpdSingleByteFunctionToken, type WpdStyleSemantics, type WpdTabEffect, type WpdToken, WpdUnsupportedVersionError, type WpdVariableFunctionToken, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
19
+ export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, type ReadWpdOptions, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, type WpdAttributeCode, WpdBytesSchema, type WpdCellFill, type WpdCellInformation, type WpdCellSpanning, type WpdCharacterToken, type WpdDiagnostic, WpdDiagnosticCodes, type WpdDiagnosticSink, type WpdDocumentContainer, type WpdEmbeddedSubfunction, type WpdEmbeddedSubfunctions, WpdEncryptedDocumentError, type WpdEolMapping, type WpdFileHeader, type WpdFixedFunctionToken, WpdFormatError, WpdNotAWordPerfectFileError, type WpdPageForm, type WpdPrefixPacket, type WpdRowInformation, type WpdRunAttributes, type WpdSingleByteFunctionToken, type WpdStyleSemantics, type WpdTabEffect, type WpdToken, WpdUnsupportedVersionError, type WpdVariableFunctionToken, WpdWrongPasswordError, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError } from "./errors.js";
1
+ import { WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError } from "./errors.js";
2
2
  import { WPD_FILE_ID, WPD_PREFIX_HEADER_SIZE, hasWordPerfectFileId, readFileHeader } from "./container/header.js";
3
3
  import { FIRST_ASCII_CHARACTER, LAST_CHARACTER, UNMAPPED_CHARACTER, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter } from "./stream/characters.js";
4
4
  import { PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, WPD_INDEX_RECORD_SIZE, packetByPrefixId, readPrefixPackets, readTypefaceName } from "./container/prefix.js";
@@ -16,4 +16,4 @@ import { FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTI
16
16
  import { readWpd, readWpdContent } from "./read.js";
17
17
  import { WpdBytesSchema, wpdContentCodec } from "./codec.js";
18
18
  import { WPD_FILE_EXTENSION, WPD_MEDIA_TYPE } from "./format.js";
19
- export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, WpdBytesSchema, WpdDiagnosticCodes, WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
19
+ export { ATTRIBUTE_OFF, ATTRIBUTE_ON, CELL_FILL_COLORS_SUBFUNCTION, CELL_INFORMATION_SUBFUNCTION, CELL_SPANNING_SUBFUNCTION, CHARACTER_DEFINE_TABLE_END, CHARACTER_TABLE_COLUMN, CHARACTER_TABLE_DEFINITION, COLUMN_GROUP, COLUMN_LEFT_MARGIN_SET, COLUMN_RIGHT_MARGIN_SET, DEFAULT_MARGIN_PT, DEFAULT_PAGE_HEIGHT_PT, DEFAULT_PAGE_WIDTH_PT, DISPLAY_NUMBER_GROUP, EOL_GROUP, FIRST_ASCII_CHARACTER, FIRST_FIXED_FUNCTION, FIRST_SINGLE_BYTE_EOL, FIRST_SINGLE_BYTE_FUNCTION, FIRST_VARIABLE_FUNCTION, LAST_CHARACTER, LAST_SINGLE_BYTE_EOL, NOOP_WPD_DIAGNOSTIC_SINK, PACKET_TYPE_DESIRED_FONT_DESCRIPTOR, PACKET_TYPE_EXTENDED_DOCUMENT_SUMMARY, PAGE_BOTTOM_MARGIN_SET, PAGE_FORM, PAGE_GROUP, PAGE_TOP_MARGIN_SET, PERFECT_OFFICE_MAIN_STREAM, PERFECT_OFFICE_OBJECTS_STORAGE, POINTS_PER_INCH, ROW_INFORMATION_SUBFUNCTION, STYLE_GROUP, TAB_GROUP, UNMAPPED_CHARACTER, WPD_FILE_EXTENSION, WPD_FILE_ID, WPD_INDEX_RECORD_SIZE, WPD_MEDIA_TYPE, WPD_PREFIX_HEADER_SIZE, WPU_PER_INCH, WpdAttribute, WpdBytesSchema, WpdDiagnosticCodes, WpdEncryptedDocumentError, WpdFormatError, WpdNotAWordPerfectFileError, WpdUnsupportedVersionError, WpdWrongPasswordError, decodeAttributeByte, decodeSingleByteCharacter, decodeWordString, decodeWpCharacter, eolMappingForSubfunction, findEmbeddedSubfunction, hasWordPerfectFileId, isParagraphNumberDisplayOff, isParagraphNumberDisplayOn, isSingleByteEol, isStyleScopeCloser, isStyleScopeOpener, openWpdDocument, packetByPrefixId, pointsFromWpu, readCellFill, readCellInformation, readCellSpanning, readDisplayNumberLevel, readDocumentSummary, readEmbeddedSubfunctions, readFileHeader, readMarginPt, readPageForm, readPrefixPackets, readRowInformation, readSystemStyleNumber, readTableColumnWidthPt, readTypefaceName, readWpd, readWpdContent, runAttributesFrom, styleSemanticsFor, subfunctionForSingleByteEol, tabEffectFor, tokeniseDocumentArea, wpdContentCodec };
package/dist/read.cjs CHANGED
@@ -683,7 +683,7 @@ function readMetadata(container) {
683
683
  }
684
684
  function readWpdContent(bytes, options = {}) {
685
685
  const sink = options.sink ?? require_diagnostics.NOOP_WPD_DIAGNOSTIC_SINK;
686
- const container = require_container_container.openWpdDocument(bytes);
686
+ const container = require_container_container.openWpdDocument(bytes, { password: options.password });
687
687
  const { blocks, page } = foldTokens(require_stream_tokenise.tokeniseDocumentArea(container.bytes, container.documentAreaOffset, container.documentAreaEnd), container, sink);
688
688
  return {
689
689
  kind: "wordprocessing",
package/dist/read.d.cts CHANGED
@@ -3,6 +3,7 @@ import { ContentDocument, DocumentTree } from "document-schema.js";
3
3
  //#region src/read.d.ts
4
4
  interface ReadWpdOptions {
5
5
  readonly sink?: WpdDiagnosticSink;
6
+ readonly password?: string;
6
7
  }
7
8
  declare function readWpdContent(bytes: Uint8Array, options?: ReadWpdOptions): ContentDocument;
8
9
  declare function readWpd(bytes: Uint8Array, options?: ReadWpdOptions): DocumentTree;
package/dist/read.d.ts CHANGED
@@ -3,6 +3,7 @@ import { ContentDocument, DocumentTree } from "document-schema.js";
3
3
  //#region src/read.d.ts
4
4
  interface ReadWpdOptions {
5
5
  readonly sink?: WpdDiagnosticSink;
6
+ readonly password?: string;
6
7
  }
7
8
  declare function readWpdContent(bytes: Uint8Array, options?: ReadWpdOptions): ContentDocument;
8
9
  declare function readWpd(bytes: Uint8Array, options?: ReadWpdOptions): DocumentTree;
package/dist/read.js CHANGED
@@ -682,7 +682,7 @@ function readMetadata(container) {
682
682
  }
683
683
  function readWpdContent(bytes, options = {}) {
684
684
  const sink = options.sink ?? NOOP_WPD_DIAGNOSTIC_SINK;
685
- const container = openWpdDocument(bytes);
685
+ const container = openWpdDocument(bytes, { password: options.password });
686
686
  const { blocks, page } = foldTokens(tokeniseDocumentArea(container.bytes, container.documentAreaOffset, container.documentAreaEnd), container, sink);
687
687
  return {
688
688
  kind: "wordprocessing",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "wpd-codec",
3
- "version": "3.2.2",
3
+ "version": "3.3.0",
4
4
  "description": "Hand-written read-only WordPerfect 6.x-X6 (.wpd) reader over document-schema.js's ContentDocument",
5
5
  "type": "module",
6
6
  "repository": {