@poe-platform/safe-bash 0.1.811 → 0.1.812

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.
Files changed (61) hide show
  1. package/dist/audio-ast/index.d.ts +1 -0
  2. package/dist/audio-ast/index.js +6 -1
  3. package/dist/audio-ast/vorbis.d.ts +14 -0
  4. package/dist/image-ast/index.js +1 -1
  5. package/dist/pdf-ast/cos/value-parser.d.ts +23 -2
  6. package/dist/pdf-ast/extract/retained-form-field-details.d.ts +20 -0
  7. package/dist/pdf-ast/extract/retained-form-fields.d.ts +17 -4
  8. package/dist/pdf-ast/index.d.ts +1 -0
  9. package/dist/pdf-ast/index.js +701 -336
  10. package/dist/pdf-ast/retained-document.d.ts +4 -0
  11. package/dist/safe-bash/audio-ast.browser.js +2 -1
  12. package/dist/safe-bash/command-chunks/{biff-3EFLKBAH-NYWZOYQS.js → biff-YKPDH35C-MVQIWNKV.js} +2309 -2277
  13. package/dist/safe-bash/command-chunks/{chunk-VU3EQF7F.js → chunk-2JSDKQ4J.js} +110 -31
  14. package/dist/safe-bash/command-chunks/{chunk-72C3TZ2U.js → chunk-3Q247UDJ.js} +1 -1
  15. package/dist/safe-bash/command-chunks/{chunk-HARUYHH7.js → chunk-5HUICAWD.js} +1 -1
  16. package/dist/safe-bash/command-chunks/{chunk-2VCKUNDZ.js → chunk-B2C3UPJS.js} +27 -17
  17. package/dist/safe-bash/command-chunks/{chunk-5LI2DLNZ.js → chunk-CJQSAATC.js} +1 -1
  18. package/dist/safe-bash/command-chunks/{chunk-ZHRGYR7B.js → chunk-FDCIPJBQ.js} +1 -1
  19. package/dist/safe-bash/command-chunks/{chunk-5MB64DWR.js → chunk-HWQ2UHMT.js} +8 -8
  20. package/dist/safe-bash/command-chunks/{chunk-5OO2P27R.js → chunk-NARD63DY.js} +98 -1
  21. package/dist/safe-bash/command-chunks/{chunk-Z5QOVRVH.js → chunk-SU26FZLJ.js} +1 -1
  22. package/dist/safe-bash/command-chunks/{chunk-DPR5CYQV.js → chunk-XITDDJFT.js} +2 -0
  23. package/dist/safe-bash/command-chunks/{chunk-YSY6R6AS.js → chunk-XVLWZTPY.js} +230 -28
  24. package/dist/safe-bash/command-chunks/{chunk-WH3TIOTS.js → chunk-ZEGNRZV2.js} +9 -2
  25. package/dist/safe-bash/command-chunks/{chunk-KL3OIBKB.js → chunk-ZEX53S5I.js} +1892 -1878
  26. package/dist/safe-bash/command-chunks/{command-engine-BEWABZ75.js → command-engine-BCUQGJJ4.js} +58 -21
  27. package/dist/safe-bash/command-chunks/{engine-AXXFTGCL-QBQNBI6K.js → engine-LAUEWYSQ-DQCEI5HE.js} +1 -1
  28. package/dist/safe-bash-command-apply-patch/apply.js +4 -4
  29. package/dist/safe-bash-command-apply-patch/index.js +4 -4
  30. package/dist/safe-bash-command-apply-patch/matcher.js +2 -2
  31. package/dist/safe-bash-command-apply-patch/parser.js +2 -2
  32. package/dist/safe-bash-command-apply-patch/shared.d.ts +2 -0
  33. package/dist/safe-bash-command-apply-patch/shared.js +1 -1
  34. package/dist/safe-bash-command-ffmpeg/index.js +1 -1
  35. package/dist/safe-bash-command-ffprobe/index.js +2 -2
  36. package/dist/safe-bash-command-ffprobe/media.js +2 -2
  37. package/dist/safe-bash-command-pandoc/command.js +1 -1
  38. package/dist/safe-bash-command-pandoc/index.js +1 -1
  39. package/dist/safe-bash-command-patch/index.js +2 -2
  40. package/dist/safe-bash-command-patch/patch-publication.js +1 -1
  41. package/dist/safe-bash-command-patch/patch.js +2 -2
  42. package/dist/safe-bash-command-pdftk/index.js +35 -2
  43. package/dist/safe-bash-command-pptx/command-engine.d.ts +12 -3
  44. package/dist/safe-bash-command-pptx/engine.d.ts +2 -2
  45. package/dist/safe-bash-command-pptx/engine.js +1 -1
  46. package/dist/safe-bash-command-ssconvert/index.js +2 -2
  47. package/dist/safe-bash-diff-engine/document.d.ts +2 -1
  48. package/dist/safe-bash-diff-engine/document.js +7 -4
  49. package/dist/safe-bash-presentation-engine/command-placeholder.js +4 -3
  50. package/dist/safe-bash-presentation-engine/index.d.ts +1 -1
  51. package/dist/safe-bash-presentation-engine/index.js +9 -7
  52. package/dist/safe-bash-presentation-engine/presentation-model.js +3 -2
  53. package/dist/safe-bash-presentation-engine/retained-slide-publication.d.ts +24 -0
  54. package/dist/safe-bash-presentation-engine/slides.d.ts +1 -0
  55. package/dist/safe-bash-presentation-engine/slides.js +6 -3
  56. package/dist/spreadsheet-format-xls/biff-encrypted-properties.d.ts +2 -2
  57. package/dist/spreadsheet-format-xls/biff-encrypted-properties.js +46 -13
  58. package/dist/spreadsheet-format-xls/biff-metadata.d.ts +1 -0
  59. package/dist/spreadsheet-format-xls/biff-metadata.js +2 -2
  60. package/dist/spreadsheet-format-xls/biff-write-metadata.js +10 -1
  61. package/package.json +2 -2
@@ -7,6 +7,6 @@ export declare function encryptedBiffPropertyStream(streams: ReadonlyMap<string,
7
7
  /** MS-OFFCRYPTO 2.3.5.4: header/table restart block 0; each payload restarts its
8
8
  * descriptor block. These are not Workbook's absolute-position 1024-byte chunks. */
9
9
  export declare function decryptBiffPropertyContainer(encrypted: Uint8Array, keyStream: (block: number, length: number) => Uint8Array, context: CapabilityContext, charge: (amount: number) => void, createCipher?: (block: number) => BiffRc4Cipher): ReadonlyMap<string, Uint8Array>;
10
- /** Decrypt retained ciphertext directly into caller storage. Only the descriptor
11
- * table is buffered; payload plaintext never accumulates in RAM. */
10
+ /** Decrypt retained ciphertext and descriptor bytes directly into caller storage.
11
+ * Parsed descriptors and names remain resident; plaintext transfers are bounded. */
12
12
  export declare function decryptBiffPropertySources(encrypted: Uint8Array | RangeSource, createCipher: (block: number) => BiffRc4Cipher, context: CapabilityContext, charge: (amount: number) => void): Promise<ReadonlyMap<string, BiffPropertySource>>;
@@ -105,7 +105,13 @@ export function decryptBiffPropertyContainer(encrypted, keyStream, context, char
105
105
  if (encrypted.length > context.limits.inputBytes)
106
106
  throw new SsconvertError("resource-limit", "ssconvert encrypted BIFF property input limit exceeded");
107
107
  const source = new Binary(encrypted), { offset, size } = propertyTableRange(decrypt(source.slice(0, 8), 0), source);
108
- const descriptors = readEncryptedPropertyDescriptors(source, offset, size, decrypt(source.slice(offset, size), 0), context, charge);
108
+ const table = new Binary(decrypt(source.slice(offset, size), 0));
109
+ const reader = readEncryptedPropertyDescriptors(source, offset, size, context, charge);
110
+ let step = reader.next();
111
+ while (!step.done)
112
+ step = reader.next(table.slice(step.value.at, step.value.size));
113
+ table.bytes.fill(0);
114
+ const descriptors = step.value;
109
115
  for (const entry of descriptors)
110
116
  result.set(entry.name, decrypt(source.slice(entry.offset, entry.size), entry.block));
111
117
  return result;
@@ -123,8 +129,8 @@ function propertyTableRange(bytes, source) {
123
129
  source.check(offset, size);
124
130
  return { offset, size };
125
131
  }
126
- function readEncryptedPropertyDescriptors(source, offset, size, bytes, context, charge) {
127
- const table = new Binary(bytes), count = table.u32(0);
132
+ function* readEncryptedPropertyDescriptors(source, offset, size, context, charge) {
133
+ const count = new Binary(yield { at: 0, size: 4 }).u32(0);
128
134
  if (count > Math.floor((size - 4) / 18))
129
135
  invalidBiff("invalid encrypted property descriptor count");
130
136
  if (count > (context.limits.workbookNodes ?? context.limits.inputBytes))
@@ -134,23 +140,25 @@ function readEncryptedPropertyDescriptors(source, offset, size, bytes, context,
134
140
  const descriptors = [], names = new Set();
135
141
  for (let i = 0; i < count; i++) {
136
142
  context.signal.throwIfAborted();
137
- table.check(at, 18);
138
- const start = table.u32(at), length = table.u32(at + 4), block = table.u16(at + 8), nameLength = table.u8(at + 10), flags = table.u8(at + 11);
139
- if (flags !== 1 || table.u32(at + 12) !== 0)
143
+ const entry = new Binary(yield { at, size: 18 });
144
+ entry.check(0, 18);
145
+ const start = entry.u32(0), length = entry.u32(4), block = entry.u16(8), nameLength = entry.u8(10), flags = entry.u8(11);
146
+ if (flags !== 1 || entry.u32(12) !== 0)
140
147
  invalidBiff("invalid encrypted property descriptor flags");
141
148
  at += 16;
142
149
  if (!nameLength || nameLength > 31)
143
150
  invalidBiff("invalid encrypted property stream name");
144
- table.check(at, (nameLength + 1) * 2);
151
+ const nameBytes = new Binary(yield { at, size: (nameLength + 1) * 2 });
152
+ nameBytes.check(0, (nameLength + 1) * 2);
145
153
  charge(nameLength);
146
- if (table.u16(at + nameLength * 2) !== 0)
154
+ if (nameBytes.u16(nameLength * 2) !== 0)
147
155
  invalidBiff("unterminated encrypted property stream name");
148
156
  textBytes += nameLength * 3;
149
157
  if (textBytes > (context.limits.workbookTextBytes ?? context.limits.inputBytes))
150
158
  throw new SsconvertError("resource-limit", "ssconvert encrypted BIFF property text limit exceeded");
151
159
  let name;
152
160
  try {
153
- name = new TextDecoder("utf-16le", { fatal: true, ignoreBOM: true }).decode(table.slice(at, nameLength * 2));
161
+ name = new TextDecoder("utf-16le", { fatal: true, ignoreBOM: true }).decode(nameBytes.slice(0, nameLength * 2));
154
162
  }
155
163
  catch {
156
164
  invalidBiff("invalid encrypted property stream name");
@@ -166,7 +174,6 @@ function readEncryptedPropertyDescriptors(source, offset, size, bytes, context,
166
174
  }
167
175
  if (at !== size)
168
176
  invalidBiff("invalid encrypted property descriptor size");
169
- table.bytes.fill(0);
170
177
  charge(count * Math.ceil(Math.log2(count + 1)));
171
178
  const ordered = [...descriptors].sort((a, b) => a.offset - b.offset);
172
179
  for (let i = 1; i < ordered.length; i++)
@@ -174,8 +181,8 @@ function readEncryptedPropertyDescriptors(source, offset, size, bytes, context,
174
181
  invalidBiff("overlapping encrypted property payloads");
175
182
  return descriptors;
176
183
  }
177
- /** Decrypt retained ciphertext directly into caller storage. Only the descriptor
178
- * table is buffered; payload plaintext never accumulates in RAM. */
184
+ /** Decrypt retained ciphertext and descriptor bytes directly into caller storage.
185
+ * Parsed descriptors and names remain resident; plaintext transfers are bounded. */
179
186
  export async function decryptBiffPropertySources(encrypted, createCipher, context, charge) {
180
187
  const result = new Map(), owned = [];
181
188
  const input = propertyRange(encrypted, context);
@@ -234,7 +241,33 @@ export async function decryptBiffPropertySources(encrypted, createCipher, contex
234
241
  return output;
235
242
  };
236
243
  const { offset, size } = propertyTableRange(await decrypt(0, 8), input);
237
- const descriptors = readEncryptedPropertyDescriptors(input, offset, size, await decrypt(offset, size), context, charge);
244
+ const table = await stagePropertyBytes({ length: size, chunks: () => chunks(offset, size, 0) }, context, context.limits.inputBytes);
245
+ const reader = readEncryptedPropertyDescriptors(input, offset, size, context, charge);
246
+ let step = reader.next();
247
+ try {
248
+ while (!step.done) {
249
+ const bytes = await table.read(step.value.at, step.value.size, { signal: context.signal });
250
+ try {
251
+ check();
252
+ step = reader.next(bytes);
253
+ }
254
+ finally {
255
+ bytes.fill(0);
256
+ }
257
+ }
258
+ }
259
+ catch (error) {
260
+ try {
261
+ await table.close();
262
+ }
263
+ catch (cleanup) {
264
+ throw new AggregateError([error, cleanup], "Encrypted BIFF descriptor read and cleanup failed");
265
+ }
266
+ throw error;
267
+ }
268
+ await table.close();
269
+ check();
270
+ const descriptors = step.value;
238
271
  for (const entry of descriptors) {
239
272
  const source = await stagePropertyBytes({ length: entry.size, chunks: () => chunks(entry.offset, entry.size, entry.block) }, context, context.limits.inputBytes);
240
273
  result.set(entry.name, source);
@@ -5,6 +5,7 @@ import { type BiffRecord } from "./biff-binary.js";
5
5
  export declare function biffNode(name: string, attributes: Readonly<Record<string, ImportedValue>>, text?: string, children?: readonly ImportedValue[]): ImportedValue;
6
6
  export declare const biffProtectionPermissions: readonly ["objects", "scenarios", "formatCells", "formatColumns", "formatRows", "insertColumns", "insertRows", "insertHyperlinks", "deleteColumns", "deleteRows", "selectLockedCells", "sort", "autoFilter", "pivotTables", "selectUnlockedCells"];
7
7
  export declare const biffMetadataOpcodes: Set<number>;
8
+ export declare function biffHeaderParts(text: string): Readonly<Record<string, string>>;
8
9
  /** Source-backed neutral records consumed by both existing workbook writers. */
9
10
  interface BiffMetadata {
10
11
  records: UnsupportedRecord[];
@@ -11,7 +11,7 @@ export const biffProtectionPermissions = ["objects", "scenarios", "formatCells",
11
11
  "sort", "autoFilter", "pivotTables", "selectUnlockedCells"];
12
12
  export const biffMetadataOpcodes = new Set([0x2a, 0x2b, 0x25, 0x225, 0x81, 0x83, 0x84, 0xa1, 0x55, 0x23e, 0x3e,
13
13
  0x1d, 0x1a, 0x1b, 0x41, 0xa0, 0x867, 0x1c, 0x1b6]);
14
- function header(text) {
14
+ export function biffHeaderParts(text) {
15
15
  const values = { Left: "", Middle: "", Right: "" };
16
16
  const substitutions = { P: "&[PAGE]", N: "&[PAGES]", D: "&[DATE]", T: "&[TIME]", F: "&[FILE]", A: "&[TAB]", Z: "&[PATH]" };
17
17
  let side = "Left";
@@ -234,7 +234,7 @@ function* metadataSteps(length, revision, codepage, context) {
234
234
  result.push({ source: "Gnumeric_XmlIO:sax", kind: "PrintInformation", disposition: "retained",
235
235
  data: biffNode("PrintInformation", {}, "", [biffNode("Margins", {}, "", Object.entries(margins).map(([name, Points]) => biffNode(name, { Points, PrefUnit: "mm" }))),
236
236
  biffNode("Scale", fitToPage ? { type: "fit", cols: fitColumns, rows: fitRows } : scale), ...Object.entries(print).map(([name, value]) => biffNode(name, { value })), biffNode("order", {}, order),
237
- biffNode("orientation", {}, orientation), biffNode("Header", header(headerText)), biffNode("Footer", header(footerText)),
237
+ biffNode("orientation", {}, orientation), biffNode("Header", biffHeaderParts(headerText)), biffNode("Footer", biffHeaderParts(footerText)),
238
238
  biffNode("paper", {}, paper), biffNode("comments", { placement: commentPlacement }), biffNode("errors", { PrintErrorsAs: errorDisplay }), ...breaks]) });
239
239
  if (objects.length)
240
240
  result.push({ source: "Gnumeric_XmlIO:sax", kind: "Objects", disposition: "retained", data: biffNode("Objects", {}, "", objects) });
@@ -3,7 +3,7 @@ import { parseA1 } from "../spreadsheet-ast/index.js";
3
3
  import { metadataNode } from "../spreadsheet-engine/codecs/xlsx-write-support.js";
4
4
  import { words } from "./biff-write-binary.js";
5
5
  import { biffString } from "./biff-write.js";
6
- import { biffProtectionPermissions } from "./biff-metadata.js";
6
+ import { biffProtectionPermissions, biffHeaderParts } from "./biff-metadata.js";
7
7
  import { biffFontWidth } from "./biff-font-widths.js";
8
8
  import { writeBiffLabelRanges } from "./biff-label-ranges.js";
9
9
  function concat(...parts) {
@@ -442,6 +442,15 @@ export class BiffMetadataWriter {
442
442
  text += source[at] === "&" ? "&&" : source[at];
443
443
  }
444
444
  }
445
+ const original = sheet.view?.[name === "Header" ? "printHeader" : "printFooter"];
446
+ if (node && typeof original === "string") {
447
+ this.charge(original.length);
448
+ const sections = biffHeaderParts(original);
449
+ // Keep the imported token spelling (including formatting controls)
450
+ // when the normalized sections are unchanged. Explicit edits win.
451
+ if (Object.entries(sections).every(([side, value]) => value === (node.attributes[side] ?? "")))
452
+ text = original;
453
+ }
445
454
  await output.record(opcode, biffString(text, revision, this.context, revision === 8 ? 2 : 1));
446
455
  }
447
456
  for (const [name, opcode] of [["hPageBreaks", 0x1b], ["vPageBreaks", 0x1a]]) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poe-platform/safe-bash",
3
- "version": "0.1.811",
3
+ "version": "0.1.812",
4
4
  "description": "Extensible virtual shell with pluggable filesystems and streaming commands",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -1407,7 +1407,7 @@
1407
1407
  "access": "public"
1408
1408
  },
1409
1409
  "dependencies": {
1410
- "@poe-platform/safe-fs": "0.1.811",
1410
+ "@poe-platform/safe-fs": "0.1.812",
1411
1411
  "pdf-lib": "1.17.1",
1412
1412
  "@types/node": "^25.2.2",
1413
1413
  "@formatjs/intl-numberformat": "9.4.0",