@cj-tech-master/excelts 9.3.1 → 9.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.
Files changed (109) hide show
  1. package/dist/browser/index.d.ts +1 -0
  2. package/dist/browser/index.js +2 -0
  3. package/dist/browser/modules/excel/cell.d.ts +18 -0
  4. package/dist/browser/modules/excel/cell.js +21 -0
  5. package/dist/browser/modules/excel/utils/cell-format.js +85 -13
  6. package/dist/browser/modules/excel/workbook.browser.d.ts +57 -0
  7. package/dist/browser/modules/excel/workbook.browser.js +49 -0
  8. package/dist/browser/modules/excel/xlsx/defaultnumformats.js +3 -3
  9. package/dist/browser/modules/formula/compile/binder.js +48 -6
  10. package/dist/browser/modules/formula/compile/bound-ast.d.ts +16 -2
  11. package/dist/browser/modules/formula/compile/bound-ast.js +1 -0
  12. package/dist/browser/modules/formula/compile/compiled-formula.js +41 -8
  13. package/dist/browser/modules/formula/functions/_shared.d.ts +19 -0
  14. package/dist/browser/modules/formula/functions/_shared.js +47 -0
  15. package/dist/browser/modules/formula/functions/conditional.js +103 -22
  16. package/dist/browser/modules/formula/functions/date.js +105 -23
  17. package/dist/browser/modules/formula/functions/dynamic-array.js +173 -69
  18. package/dist/browser/modules/formula/functions/engineering.d.ts +2 -2
  19. package/dist/browser/modules/formula/functions/engineering.js +103 -151
  20. package/dist/browser/modules/formula/functions/financial.js +210 -184
  21. package/dist/browser/modules/formula/functions/lookup.js +224 -157
  22. package/dist/browser/modules/formula/functions/math.d.ts +26 -0
  23. package/dist/browser/modules/formula/functions/math.js +249 -69
  24. package/dist/browser/modules/formula/functions/statistical.js +221 -171
  25. package/dist/browser/modules/formula/functions/text.js +112 -52
  26. package/dist/browser/modules/formula/integration/calculate-formulas-impl.js +20 -1
  27. package/dist/browser/modules/formula/materialize/build-writeback-plan.js +10 -6
  28. package/dist/browser/modules/formula/materialize/types.d.ts +15 -0
  29. package/dist/browser/modules/formula/runtime/evaluator.d.ts +8 -0
  30. package/dist/browser/modules/formula/runtime/evaluator.js +582 -162
  31. package/dist/browser/modules/formula/runtime/function-registry.d.ts +5 -0
  32. package/dist/browser/modules/formula/runtime/function-registry.js +59 -13
  33. package/dist/browser/modules/formula/runtime/values.d.ts +13 -0
  34. package/dist/browser/modules/formula/runtime/values.js +20 -2
  35. package/dist/browser/modules/formula/syntax/ast.d.ts +14 -2
  36. package/dist/browser/modules/formula/syntax/ast.js +1 -0
  37. package/dist/browser/modules/formula/syntax/parser.js +29 -7
  38. package/dist/browser/modules/formula/syntax/token-types.d.ts +4 -0
  39. package/dist/browser/modules/formula/syntax/token-types.js +9 -0
  40. package/dist/browser/modules/formula/syntax/tokenizer.js +76 -19
  41. package/dist/cjs/index.js +7 -2
  42. package/dist/cjs/modules/excel/cell.js +21 -0
  43. package/dist/cjs/modules/excel/utils/cell-format.js +85 -13
  44. package/dist/cjs/modules/excel/workbook.browser.js +49 -0
  45. package/dist/cjs/modules/excel/xlsx/defaultnumformats.js +3 -3
  46. package/dist/cjs/modules/formula/compile/binder.js +48 -6
  47. package/dist/cjs/modules/formula/compile/compiled-formula.js +41 -8
  48. package/dist/cjs/modules/formula/functions/_shared.js +48 -0
  49. package/dist/cjs/modules/formula/functions/conditional.js +103 -22
  50. package/dist/cjs/modules/formula/functions/date.js +104 -22
  51. package/dist/cjs/modules/formula/functions/dynamic-array.js +173 -69
  52. package/dist/cjs/modules/formula/functions/engineering.js +109 -157
  53. package/dist/cjs/modules/formula/functions/financial.js +209 -183
  54. package/dist/cjs/modules/formula/functions/lookup.js +224 -157
  55. package/dist/cjs/modules/formula/functions/math.js +254 -70
  56. package/dist/cjs/modules/formula/functions/statistical.js +222 -172
  57. package/dist/cjs/modules/formula/functions/text.js +112 -52
  58. package/dist/cjs/modules/formula/integration/calculate-formulas-impl.js +20 -1
  59. package/dist/cjs/modules/formula/materialize/build-writeback-plan.js +10 -6
  60. package/dist/cjs/modules/formula/runtime/evaluator.js +581 -161
  61. package/dist/cjs/modules/formula/runtime/function-registry.js +57 -11
  62. package/dist/cjs/modules/formula/runtime/values.js +21 -2
  63. package/dist/cjs/modules/formula/syntax/parser.js +29 -7
  64. package/dist/cjs/modules/formula/syntax/token-types.js +9 -0
  65. package/dist/cjs/modules/formula/syntax/tokenizer.js +76 -19
  66. package/dist/esm/index.js +2 -0
  67. package/dist/esm/modules/excel/cell.js +21 -0
  68. package/dist/esm/modules/excel/utils/cell-format.js +85 -13
  69. package/dist/esm/modules/excel/workbook.browser.js +49 -0
  70. package/dist/esm/modules/excel/xlsx/defaultnumformats.js +3 -3
  71. package/dist/esm/modules/formula/compile/binder.js +48 -6
  72. package/dist/esm/modules/formula/compile/bound-ast.js +1 -0
  73. package/dist/esm/modules/formula/compile/compiled-formula.js +41 -8
  74. package/dist/esm/modules/formula/functions/_shared.js +47 -0
  75. package/dist/esm/modules/formula/functions/conditional.js +103 -22
  76. package/dist/esm/modules/formula/functions/date.js +105 -23
  77. package/dist/esm/modules/formula/functions/dynamic-array.js +173 -69
  78. package/dist/esm/modules/formula/functions/engineering.js +103 -151
  79. package/dist/esm/modules/formula/functions/financial.js +210 -184
  80. package/dist/esm/modules/formula/functions/lookup.js +224 -157
  81. package/dist/esm/modules/formula/functions/math.js +249 -69
  82. package/dist/esm/modules/formula/functions/statistical.js +221 -171
  83. package/dist/esm/modules/formula/functions/text.js +112 -52
  84. package/dist/esm/modules/formula/integration/calculate-formulas-impl.js +20 -1
  85. package/dist/esm/modules/formula/materialize/build-writeback-plan.js +10 -6
  86. package/dist/esm/modules/formula/runtime/evaluator.js +582 -162
  87. package/dist/esm/modules/formula/runtime/function-registry.js +59 -13
  88. package/dist/esm/modules/formula/runtime/values.js +20 -2
  89. package/dist/esm/modules/formula/syntax/ast.js +1 -0
  90. package/dist/esm/modules/formula/syntax/parser.js +29 -7
  91. package/dist/esm/modules/formula/syntax/token-types.js +9 -0
  92. package/dist/esm/modules/formula/syntax/tokenizer.js +76 -19
  93. package/dist/iife/excelts.iife.js +1502 -1379
  94. package/dist/iife/excelts.iife.js.map +1 -1
  95. package/dist/iife/excelts.iife.min.js +26 -26
  96. package/dist/types/index.d.ts +1 -0
  97. package/dist/types/modules/excel/cell.d.ts +18 -0
  98. package/dist/types/modules/excel/workbook.browser.d.ts +57 -0
  99. package/dist/types/modules/formula/compile/bound-ast.d.ts +16 -2
  100. package/dist/types/modules/formula/functions/_shared.d.ts +19 -0
  101. package/dist/types/modules/formula/functions/engineering.d.ts +2 -2
  102. package/dist/types/modules/formula/functions/math.d.ts +26 -0
  103. package/dist/types/modules/formula/materialize/types.d.ts +15 -0
  104. package/dist/types/modules/formula/runtime/evaluator.d.ts +8 -0
  105. package/dist/types/modules/formula/runtime/function-registry.d.ts +5 -0
  106. package/dist/types/modules/formula/runtime/values.d.ts +13 -0
  107. package/dist/types/modules/formula/syntax/ast.d.ts +14 -2
  108. package/dist/types/modules/formula/syntax/token-types.d.ts +4 -0
  109. package/package.json +1 -1
@@ -35,6 +35,7 @@ export type { NodeInput } from "./modules/excel/stream/workbook-reader.js";
35
35
  export { decodeCol, encodeCol, decodeRow, encodeRow, decodeCell, encodeCell, decodeRange, encodeRange } from "./modules/excel/utils/address.js";
36
36
  export type { CellAddress, SheetRange, Origin } from "./modules/excel/utils/address.js";
37
37
  export type { SheetToJSONOptions, AddJSONOptions, AddAOAOptions } from "./modules/excel/worksheet.js";
38
+ export { getCellDisplayText, formatCellValue, isDateDisplayFormat } from "./modules/excel/utils/cell-format.js";
38
39
  export { dateToExcel, excelToDate } from "./utils/utils.base.js";
39
40
  export { base64ToUint8Array, uint8ArrayToBase64 } from "./utils/utils.base.js";
40
41
  export { xmlEncode, xmlDecode } from "./modules/xml/encode.js";
@@ -130,6 +130,24 @@ declare class Cell {
130
130
  get comment(): Note | undefined;
131
131
  set comment(comment: Note | NoteConfig | undefined);
132
132
  get text(): string;
133
+ /**
134
+ * The cell's display text — the value formatted the way Excel would render
135
+ * it, applying the cell's `numFmt`. For a Date cell with `numFmt` `"mm-dd-yy"`,
136
+ * this returns e.g. `"04-12-19"` rather than the JS `Date.prototype.toString()`
137
+ * output you'd get from `cell.text`.
138
+ *
139
+ * Handles primitive values, dates, and formula results. For rich text,
140
+ * hyperlinks, errors, and other complex types, falls back to `cell.text`.
141
+ *
142
+ * Note: numFmt codes that are locale-dependent in Excel (e.g. built-in
143
+ * numFmtId 14 renders as `dd.mm.yyyy` under German locale but is stored
144
+ * as `mm-dd-yy`) are applied literally — excelts does not perform
145
+ * Excel's locale-based format substitution. If you need a specific date
146
+ * style across cells regardless of per-cell numFmts, call the exported
147
+ * {@link getCellDisplayText} helper with a `dateFormat` argument, or use
148
+ * `worksheet.toJSON({ dateFormat })`.
149
+ */
150
+ get displayText(): string;
133
151
  get html(): string;
134
152
  toString(): string;
135
153
  get formula(): string | undefined;
@@ -603,6 +603,63 @@ declare class Workbook {
603
603
  * ```
604
604
  */
605
605
  calculateFormulas(): void;
606
+ /**
607
+ * Per-workbook registry of user-defined functions. The formula engine
608
+ * consults this map before the built-in 433-function registry, so a
609
+ * registered name either adds a new function (`MYFN`) or shadows a
610
+ * built-in (`IRR` → project-specific variant).
611
+ *
612
+ * Populated by {@link registerFunction}; read by the formula engine
613
+ * when the host calls `calculateFormulas()` — see
614
+ * `@formula/runtime/evaluator.ts::evaluateCall`.
615
+ */
616
+ userFunctions?: Map<string, {
617
+ minArity: number;
618
+ maxArity: number;
619
+ invoke: (args: unknown[]) => unknown;
620
+ volatile?: boolean;
621
+ }>;
622
+ /**
623
+ * Register (or replace) a custom formula function on this workbook.
624
+ *
625
+ * The function becomes visible to `calculateFormulas()` on this
626
+ * workbook only — the built-in registry stays untouched. Names are
627
+ * case-insensitive (normalised to uppercase) and must not include
628
+ * the `_XLFN.` prefix — the engine strips that automatically.
629
+ *
630
+ * @param name Function name (case-insensitive).
631
+ * @param fn Implementation. Receives already-evaluated RuntimeValue
632
+ * arguments; return a RuntimeValue. Wrap failures with
633
+ * `rvError("#VALUE!")` rather than throwing — throws are
634
+ * caught at the evaluator boundary and surface as
635
+ * `#VALUE!` so a buggy custom function doesn't tear
636
+ * down the whole calculation pass.
637
+ * @param options Optional arity bounds. Defaults to `minArity=0`,
638
+ * `maxArity=255` (Excel's universal argument cap), so
639
+ * simple variadic functions work without extra config.
640
+ * Set `volatile: true` when the function should be
641
+ * re-evaluated on every calc cycle (analogous to
642
+ * built-in `RAND`, `NOW`). Currently reserved for
643
+ * future use; the engine recomputes every formula on
644
+ * each `calculateFormulas()` call regardless.
645
+ *
646
+ * ```ts
647
+ * import { rvNumber } from "@cj-tech-master/excelts/formula";
648
+ * workbook.registerFunction("DOUBLE", ([x]) => {
649
+ * return rvNumber((x as any).value * 2);
650
+ * }, { minArity: 1, maxArity: 1 });
651
+ * ```
652
+ */
653
+ registerFunction(name: string, fn: (args: unknown[]) => unknown, options?: {
654
+ minArity?: number;
655
+ maxArity?: number;
656
+ volatile?: boolean;
657
+ }): void;
658
+ /**
659
+ * Remove a user-registered function. No-op when the name isn't
660
+ * registered; returns `true` when an entry was removed.
661
+ */
662
+ unregisterFunction(name: string): boolean;
606
663
  clearThemes(): void;
607
664
  /**
608
665
  * Add Image to Workbook and return the id
@@ -46,7 +46,8 @@ export declare const enum BoundExprKind {
46
46
  Array = 12,
47
47
  NameExpr = 13,
48
48
  Lambda = 14,
49
- StructuredRef = 15
49
+ StructuredRef = 15,
50
+ UnionRef = 16
50
51
  }
51
52
  /**
52
53
  * A resolved literal value.
@@ -220,7 +221,20 @@ export interface BoundStructuredRef {
220
221
  /** Special items (#Headers, #Data, #Totals, #All, #This Row). */
221
222
  readonly specials: readonly string[];
222
223
  }
223
- export type BoundExpr = BoundLiteral | BoundCellRef | BoundAreaRef | BoundColRangeRef | BoundRowRangeRef | BoundRef3D | BoundBinaryOp | BoundUnaryOp | BoundPercent | BoundCall | BoundSpecialCall | BoundArray | BoundNameExpr | BoundLambda | BoundStructuredRef;
224
+ /**
225
+ * A union of reference-producing sub-expressions — `(A1:B2, D4:E5)`.
226
+ *
227
+ * Produced only by parenthesised comma lists, and only used by callers
228
+ * that explicitly know how to consume a multi-area reference (INDEX's
229
+ * `area_num`, AREAS, union-operator arithmetic). Evaluating a
230
+ * UnionRef in any other context surfaces as `#VALUE!` since Excel
231
+ * forbids arithmetic / coercion on disjoint areas.
232
+ */
233
+ export interface BoundUnionRef {
234
+ readonly kind: BoundExprKind.UnionRef;
235
+ readonly areas: readonly BoundExpr[];
236
+ }
237
+ export type BoundExpr = BoundLiteral | BoundCellRef | BoundAreaRef | BoundColRangeRef | BoundRowRangeRef | BoundRef3D | BoundBinaryOp | BoundUnaryOp | BoundPercent | BoundCall | BoundSpecialCall | BoundArray | BoundNameExpr | BoundLambda | BoundStructuredRef | BoundUnionRef;
224
238
  export declare function boundLiteral(value: number | string | boolean | null, errorCode?: string): BoundLiteral;
225
239
  export declare function boundCellRef(sheet: string, row: number, col: number): BoundCellRef;
226
240
  export declare function boundAreaRef(sheet: string, top: number, left: number, bottom: number, right: number): BoundAreaRef;
@@ -33,6 +33,25 @@ export declare function argToNumber(arg: RuntimeValue): NumberValue | ErrorValue
33
33
  * `number[]` after an error check should map `.value` themselves.
34
34
  */
35
35
  export declare function flattenNumbers(args: RuntimeValue[]): (NumberValue | ErrorValue)[];
36
+ /**
37
+ * Streaming fold over numeric arguments.
38
+ *
39
+ * Same selection rules as `flattenNumbers` (array cells contribute only
40
+ * Number/Error; direct scalar coercion via `toNumberRV`; blanks dropped),
41
+ * but the caller's `onNumber` callback fires inline — no intermediate
42
+ * array is allocated. On the first error encountered the scan short-
43
+ * circuits and returns that error.
44
+ *
45
+ * Returns:
46
+ * - `null` when iteration finished without encountering an error, or
47
+ * - the `ErrorValue` that aborted the scan.
48
+ *
49
+ * Prefer this over `flattenNumbers` + `firstError` + manual loop in hot
50
+ * aggregates (SUM / AVERAGE / MIN / MAX / …). The allocation saved is
51
+ * one `NumberValue | ErrorValue` array per invocation — meaningful
52
+ * when the engine sums tens of thousands of cells.
53
+ */
54
+ export declare function forEachNumber(args: readonly RuntimeValue[], onNumber: (n: number) => void): ErrorValue | null;
36
55
  /**
37
56
  * Flatten all cells from the arguments into a flat list of ScalarValue,
38
57
  * preserving every cell (including blanks, errors, booleans, strings).
@@ -5,10 +5,10 @@ import type { RuntimeValue } from "../runtime/values.js";
5
5
  type NativeFn = (args: RuntimeValue[]) => RuntimeValue;
6
6
  export declare const fnBIN2DEC: NativeFn;
7
7
  export declare const fnDEC2BIN: NativeFn;
8
- export declare const fnHEX2DEC: NativeFn;
9
8
  export declare const fnDEC2HEX: NativeFn;
10
- export declare const fnOCT2DEC: NativeFn;
11
9
  export declare const fnDEC2OCT: NativeFn;
10
+ export declare const fnHEX2DEC: NativeFn;
11
+ export declare const fnOCT2DEC: NativeFn;
12
12
  export declare const fnBIN2HEX: NativeFn;
13
13
  export declare const fnBIN2OCT: NativeFn;
14
14
  export declare const fnHEX2BIN: NativeFn;
@@ -42,7 +42,33 @@ export declare const fnPRODUCT: NativeFn;
42
42
  export declare const fnSUMPRODUCT: NativeFn;
43
43
  export declare const fnABS: NativeFn;
44
44
  export declare const fnCEILING: NativeFn;
45
+ /**
46
+ * CEILING.MATH(number, [significance], [mode]) — rounds away from zero
47
+ * by default, or toward zero when `mode` is non-zero AND `number` is
48
+ * negative. Significance is always interpreted by absolute value.
49
+ *
50
+ * Different from CEILING: negative numbers with positive significance
51
+ * are valid (Excel does NOT require same sign), and there is an extra
52
+ * `mode` switch that flips the rounding direction for negatives.
53
+ */
54
+ export declare const fnCEILING_MATH: NativeFn;
55
+ /**
56
+ * CEILING.PRECISE / ISO.CEILING — always rounds toward +∞ (irrespective
57
+ * of sign), using the absolute value of significance.
58
+ */
59
+ export declare const fnCEILING_PRECISE: NativeFn;
45
60
  export declare const fnFLOOR: NativeFn;
61
+ /**
62
+ * FLOOR.MATH(number, [significance], [mode]) — rounds toward zero by
63
+ * default, or away from zero when `mode` is non-zero AND `number` is
64
+ * negative. Uses `|significance|` so negative significance never
65
+ * produces #NUM!.
66
+ */
67
+ export declare const fnFLOOR_MATH: NativeFn;
68
+ /**
69
+ * FLOOR.PRECISE — always rounds toward −∞ using `|significance|`.
70
+ */
71
+ export declare const fnFLOOR_PRECISE: NativeFn;
46
72
  export declare const fnINT: NativeFn;
47
73
  export declare const fnMOD: NativeFn;
48
74
  export declare const fnPOWER: NativeFn;
@@ -159,6 +159,21 @@ export interface WorkbookLike {
159
159
  properties?: {
160
160
  date1904?: boolean;
161
161
  };
162
+ /**
163
+ * User-registered custom functions exposed to the formula engine.
164
+ * Keys are uppercase canonical names; values are arity + invoke
165
+ * descriptors. When the evaluator encounters a call it consults this
166
+ * map before the global built-in registry, so users can shadow a
167
+ * built-in (e.g. replace `IRR` with a domain-specific variant) or
168
+ * add entirely new names.
169
+ */
170
+ userFunctions?: ReadonlyMap<string, {
171
+ minArity: number;
172
+ maxArity: number;
173
+ invoke: (args: unknown[]) => unknown;
174
+ /** Reserved for future volatile-function wiring. */
175
+ volatile?: boolean;
176
+ }>;
162
177
  }
163
178
  /**
164
179
  * Tracks a spill region: the source formula cell and the range of cells it
@@ -8,6 +8,7 @@
8
8
  import type { BoundExpr } from "../compile/bound-ast.js";
9
9
  import type { CompiledFormula } from "../compile/compiled-formula.js";
10
10
  import type { WorkbookSnapshot } from "../integration/workbook-snapshot.js";
11
+ import type { FunctionDescriptor } from "./function-registry.js";
11
12
  import type { RuntimeValue } from "./values.js";
12
13
  /**
13
14
  * Cached formula evaluation result with both scalar and raw forms.
@@ -114,6 +115,13 @@ export interface EvalContext {
114
115
  };
115
116
  /** Local variable bindings from LET expressions. */
116
117
  localBindings?: Map<string, RuntimeValue>;
118
+ /**
119
+ * User-registered functions that take precedence over the built-in
120
+ * registry. Lookup happens in `evaluateCall` — a matching
121
+ * descriptor here shadows any built-in of the same name. Keys are
122
+ * canonical uppercase names (prefix-stripped on register).
123
+ */
124
+ readonly userFunctions?: ReadonlyMap<string, FunctionDescriptor>;
117
125
  }
118
126
  /**
119
127
  * Evaluate a BoundExpr to produce a RuntimeValue.
@@ -38,6 +38,11 @@ export declare function registerFunction(desc: FunctionDescriptor): void;
38
38
  * `_XLFN._XLWS.` prefixed variants by stripping the prefix before lookup
39
39
  * (a no-op for plain names, so plain lookups also go through a single
40
40
  * Map.get call — avoiding the double-lookup pattern used previously).
41
+ *
42
+ * Fast-path: the overwhelming majority of lookups use plain names
43
+ * (`SUM`, `IF`, `VLOOKUP`, …). Checking the prefix sentinel byte up
44
+ * front lets those callers skip the `slice`/`startsWith` machinery in
45
+ * `stripFunctionPrefix` entirely.
41
46
  */
42
47
  export declare function lookupFunction(name: string): FunctionDescriptor | undefined;
43
48
  /**
@@ -156,6 +156,19 @@ export declare function rvString(value: string): StringValue;
156
156
  export declare function rvBoolean(value: boolean): BooleanValue;
157
157
  export declare function rvError(code: ErrorCode): ErrorValue;
158
158
  export declare function rvArray(rows: ScalarValue[][], originRow?: number, originCol?: number, subtotalMask?: readonly (readonly boolean[])[], hiddenRowMask?: readonly boolean[]): ArrayValue;
159
+ /**
160
+ * Fast-path rectangular ArrayValue constructor.
161
+ *
162
+ * Callers that have already produced strictly-rectangular `rows` (every
163
+ * row is the same length — the length they explicitly `new Array(width)`
164
+ * allocated) can skip the two-pass width-scan + padding loop in
165
+ * `rvArray`. Examples: `buildRangeArray`, `broadcastBinaryOp`,
166
+ * `evaluateArrayLiteral`, `TRANSPOSE` — they all know `width` up front.
167
+ *
168
+ * Rows MUST be rectangular; passing ragged data will silently surface as
169
+ * `undefined` cells downstream.
170
+ */
171
+ export declare function rvArrayRect(rows: ScalarValue[][], height: number, width: number, originRow?: number, originCol?: number, subtotalMask?: readonly (readonly boolean[])[], hiddenRowMask?: readonly boolean[]): ArrayValue;
159
172
  export declare function rvRef(sheet: string, top: number, left: number, bottom: number, right: number): ReferenceValue;
160
173
  export declare function rvCellRef(sheet: string, row: number, col: number): ReferenceValue;
161
174
  export declare function rvLambda(params: string[], body: BoundExpr, closureBindings?: ReadonlyMap<string, RuntimeValue>): LambdaValue;
@@ -20,7 +20,8 @@ export declare const enum NodeType {
20
20
  ColRangeRef = 13,
21
21
  RowRangeRef = 14,
22
22
  StructuredRef = 15,
23
- Missing = 16
23
+ Missing = 16,
24
+ UnionRef = 17
24
25
  }
25
26
  export interface NumberNode {
26
27
  type: NodeType.Number;
@@ -126,4 +127,15 @@ export interface StructuredRefNode {
126
127
  export interface MissingNode {
127
128
  type: NodeType.Missing;
128
129
  }
129
- export type AstNode = NumberNode | StringNode | BooleanNode | ErrorNode | CellRefNode | RangeRefNode | BinaryOpNode | UnaryOpNode | FunctionCallNode | ArrayNode | PercentNode | NameNode | ColRangeRefNode | RowRangeRefNode | StructuredRefNode | MissingNode;
130
+ /**
131
+ * A reference union produced by the comma operator inside
132
+ * parentheses — `(A1:B2, D4:E5)`. Each member is itself a
133
+ * reference-producing sub-expression. INDEX's `area_num` parameter
134
+ * selects which element of the union to read.
135
+ */
136
+ export interface UnionRefNode {
137
+ type: NodeType.UnionRef;
138
+ /** The union members, in syntactic order. */
139
+ areas: AstNode[];
140
+ }
141
+ export type AstNode = NumberNode | StringNode | BooleanNode | ErrorNode | CellRefNode | RangeRefNode | BinaryOpNode | UnaryOpNode | FunctionCallNode | ArrayNode | PercentNode | NameNode | ColRangeRefNode | RowRangeRefNode | StructuredRefNode | MissingNode | UnionRefNode;
@@ -148,6 +148,10 @@ export interface IntersectToken {
148
148
  * The input may or may not already be uppercased — this helper does not
149
149
  * alter case; callers that compare against an uppercase table should
150
150
  * uppercase first (or compare case-insensitively).
151
+ *
152
+ * Fast path: plain names (99%+ of call sites) start with a letter, so
153
+ * checking the first code unit before the `startsWith` machinery lets
154
+ * those lookups skip the allocation.
151
155
  */
152
156
  export declare function stripFunctionPrefix(name: string): string;
153
157
  export type Token = NumberToken | StringToken | BooleanToken | ErrorToken | CellRefToken | RangeToken | SheetRefToken | FunctionToken | OperatorToken | OpenParenToken | CloseParenToken | CommaToken | ColonToken | PercentToken | OpenBraceToken | CloseBraceToken | SemicolonToken | UnaryPrefixToken | NameToken | ColRangeToken | RowRangeToken | StructuredRefToken | AtSignToken | IntersectToken;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cj-tech-master/excelts",
3
- "version": "9.3.1",
3
+ "version": "9.4.0",
4
4
  "description": "Zero-dependency TypeScript toolkit — Excel (XLSX), PDF, CSV, Markdown, XML, ZIP/TAR, and streaming.",
5
5
  "keywords": [
6
6
  "archive",