@particle-academy/holy-sheet 1.0.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.
@@ -0,0 +1,420 @@
1
+ /**
2
+ * Public input schema + result types. Mirrors the PHP package's array shapes.
3
+ * Inputs are intentionally permissive (agents emit loose JSON) — the Validator
4
+ * is the gate, not the type system.
5
+ */
6
+ type ThemeKey = "default" | "minimal" | "plain" | "business";
7
+ type ColumnType = "auto" | "string" | "number" | "integer" | "boolean" | "date" | "datetime" | "currency" | "percent" | "formula";
8
+ interface ColumnSchema {
9
+ header: string;
10
+ type?: ColumnType;
11
+ currency?: string;
12
+ decimals?: number;
13
+ format?: string;
14
+ width?: number;
15
+ }
16
+ type DisplayFormat = "auto" | "text" | "number" | "date" | "datetime" | "percentage" | "currency";
17
+ interface CellFormatInput {
18
+ bold?: boolean;
19
+ italic?: boolean;
20
+ textAlign?: "left" | "center" | "right";
21
+ displayFormat?: DisplayFormat;
22
+ decimals?: number;
23
+ color?: string;
24
+ backgroundColor?: string;
25
+ fontSize?: number;
26
+ borderTop?: string | null;
27
+ borderRight?: string | null;
28
+ borderBottom?: string | null;
29
+ borderLeft?: string | null;
30
+ currency?: string;
31
+ }
32
+ interface CommentInput {
33
+ text: string;
34
+ author?: string;
35
+ color?: string;
36
+ }
37
+ type CellPrimitive = string | number | boolean | null;
38
+ interface CellData {
39
+ value?: CellPrimitive;
40
+ formula?: string;
41
+ computedValue?: CellPrimitive;
42
+ format?: CellFormatInput;
43
+ comment?: CommentInput;
44
+ }
45
+ type RowCell = CellPrimitive | CellData;
46
+ type AggOp = "sum" | "avg" | "count" | "min" | "max";
47
+ interface SheetSchema {
48
+ name: string;
49
+ columns?: ColumnSchema[];
50
+ rows?: RowCell[][];
51
+ theme?: ThemeKey;
52
+ totals?: Record<string, AggOp | string>;
53
+ cells?: Record<string, CellData>;
54
+ mergedRegions?: {
55
+ start: string;
56
+ end: string;
57
+ }[];
58
+ columnWidths?: Record<number | string, number>;
59
+ frozenRows?: number;
60
+ frozenCols?: number;
61
+ }
62
+ interface HolySheetSchema {
63
+ sheets: SheetSchema[];
64
+ meta?: {
65
+ creator?: string;
66
+ created?: string;
67
+ };
68
+ }
69
+ interface ValidationError {
70
+ path: string;
71
+ expected: string;
72
+ got: string;
73
+ value: unknown;
74
+ hint: string;
75
+ }
76
+ interface FormulaProblem {
77
+ sheet: string;
78
+ address: string;
79
+ formula: string;
80
+ error: string;
81
+ hint: string;
82
+ }
83
+ interface WriteResult {
84
+ path: string;
85
+ bytes: number;
86
+ sheets: number;
87
+ }
88
+ interface RepairResult {
89
+ schema: Record<string, unknown>;
90
+ errors: ValidationError[];
91
+ repairs: string[];
92
+ }
93
+ /** Options passed through ArrayBuilder / CsvBuilder. */
94
+ interface BuilderOptions {
95
+ theme?: ThemeKey;
96
+ currency?: string;
97
+ totals?: Record<string, AggOp | string>;
98
+ frozenRows?: number;
99
+ frozenCols?: number;
100
+ sheetName?: string;
101
+ delimiter?: string;
102
+ enclosure?: string;
103
+ }
104
+
105
+ /** Feature-parity baseline with PHP holy-sheet; bumped independently on npm. */
106
+ declare const VERSION = "1.0.0";
107
+ type Any$5 = any;
108
+ /**
109
+ * Agent — the structured-tool surface for Holy Sheet. Mirrors PHP `Agent`.
110
+ * Universal methods are synchronous; file-touching methods (`write`,
111
+ * `describe`-from-path) are async and Node-only (browsers have no sync FS).
112
+ */
113
+ declare const Agent: {
114
+ /** Validate a schema without writing. Empty array = valid. */
115
+ validate(schema: Any$5): ValidationError[];
116
+ /** xlsx bytes without touching disk. Universal. Throws SchemaException if invalid. */
117
+ toBytes(schema: Any$5): Uint8Array;
118
+ /** Write a workbook to disk (Node only). Throws SchemaException if invalid. */
119
+ write(schema: Any$5, path: string): Promise<WriteResult>;
120
+ /** JSON Schema for LLM tool-use. */
121
+ toolDefinition(): Record<string, unknown>;
122
+ /** Round-trip xlsx bytes back to a schema. Universal. */
123
+ read(input: Uint8Array | ArrayBuffer): Record<string, unknown>;
124
+ /** Round-trip an xlsx file on disk back to a schema (Node only). */
125
+ describe(path: string): Promise<Record<string, unknown>>;
126
+ /** Validate + conservative repairs in one call. */
127
+ validateAndRepair(schema: Any$5): RepairResult;
128
+ /** Build a schema from a flat array of rows (+ optional headers). */
129
+ fromArray(rows: Any$5[][], headers?: string[] | null, sheetName?: string, options?: BuilderOptions): HolySheetSchema;
130
+ /** Build a schema from CSV content (read files yourself in Node). */
131
+ fromCsv(csv: string, options?: BuilderOptions): HolySheetSchema;
132
+ /** Evaluate every formula and report Excel-style errors. Empty array = clean. */
133
+ lint(schema: Any$5): FormulaProblem[];
134
+ version(): string;
135
+ };
136
+
137
+ type Any$4 = any;
138
+ /**
139
+ * Holy Sheet — instance entry point mirroring PHP `HolySheet`. Thin wrappers
140
+ * over `Agent`. Provided for parity / DI ergonomics; most callers use `Agent`.
141
+ */
142
+ declare class HolySheet {
143
+ static readonly VERSION = "1.0.0";
144
+ validate(schema: Any$4): ValidationError[];
145
+ toBytes(schema: Any$4): Uint8Array;
146
+ write(schema: Any$4, path: string): Promise<WriteResult>;
147
+ toolDefinition(): Record<string, unknown>;
148
+ read(input: Uint8Array | ArrayBuffer): Record<string, unknown>;
149
+ describe(path: string): Promise<Record<string, unknown>>;
150
+ validateAndRepair(schema: Any$4): RepairResult;
151
+ fromArray(rows: Any$4[][], headers?: string[] | null, sheetName?: string, options?: BuilderOptions): HolySheetSchema;
152
+ fromCsv(csv: string, options?: BuilderOptions): HolySheetSchema;
153
+ lint(schema: Any$4): FormulaProblem[];
154
+ getVersion(): string;
155
+ static version(): string;
156
+ }
157
+
158
+ /** Thrown when a Holy Sheet schema fails validation. Mirrors PHP `SchemaException`. */
159
+ declare class SchemaException extends Error {
160
+ readonly errors: ValidationError[];
161
+ constructor(errors: ValidationError[], message?: string);
162
+ static fromErrors(errors: ValidationError[]): SchemaException;
163
+ getErrors(): ValidationError[];
164
+ }
165
+
166
+ type Any$3 = any;
167
+ /** Hand-rolled schema validator. Mirrors PHP `Schema\Validator`. */
168
+ declare class Validator {
169
+ validate(schema: Any$3): ValidationError[];
170
+ assert(schema: Any$3): void;
171
+ validateAndRepair(schema: Any$3): RepairResult;
172
+ private validateSheet;
173
+ private validateColumn;
174
+ }
175
+
176
+ type Any$2 = any;
177
+ /**
178
+ * Conservative, high-confidence schema repairs. Mirrors PHP `Schema\Repairer`.
179
+ * Returns [repairedSchema, repairs].
180
+ */
181
+ declare class Repairer {
182
+ private repairs;
183
+ repair(schema: Any$2): [Record<string, unknown>, string[]];
184
+ private repairTopLevel;
185
+ private repairSheet;
186
+ private repairColumnTypeInference;
187
+ private repairStringifiedNumerics;
188
+ }
189
+
190
+ declare class CellComment {
191
+ readonly text: string;
192
+ readonly author: string | null;
193
+ readonly color: string | null;
194
+ constructor(text: string, author?: string | null, color?: string | null);
195
+ }
196
+
197
+ interface CellFormatProps {
198
+ bold?: boolean;
199
+ italic?: boolean;
200
+ textAlign?: string | null;
201
+ displayFormat?: DisplayFormat | null;
202
+ decimals?: number | null;
203
+ color?: string | null;
204
+ backgroundColor?: string | null;
205
+ fontSize?: number | null;
206
+ borderTop?: string | null;
207
+ borderRight?: string | null;
208
+ borderBottom?: string | null;
209
+ borderLeft?: string | null;
210
+ currency?: string | null;
211
+ }
212
+ /**
213
+ * Per-cell format. The writer's StylesRegistry deduplicates equal formats.
214
+ * Mirrors PHP `Workbook\CellFormat` (PHP named args → an options object here).
215
+ */
216
+ declare class CellFormat {
217
+ readonly bold: boolean;
218
+ readonly italic: boolean;
219
+ readonly textAlign: string | null;
220
+ readonly displayFormat: DisplayFormat | null;
221
+ readonly decimals: number | null;
222
+ readonly color: string | null;
223
+ readonly backgroundColor: string | null;
224
+ readonly fontSize: number | null;
225
+ readonly borderTop: string | null;
226
+ readonly borderRight: string | null;
227
+ readonly borderBottom: string | null;
228
+ readonly borderLeft: string | null;
229
+ readonly currency: string | null;
230
+ constructor(p?: CellFormatProps);
231
+ /** Stable dedup key (JSON of ordered fields — replaces PHP md5(serialize)). */
232
+ key(): string;
233
+ isEmpty(): boolean;
234
+ static fromInput(a: CellFormatInput): CellFormat;
235
+ /** Merge another format on top of this one (other wins where set). */
236
+ mergeWith(other: CellFormat | null): CellFormat;
237
+ }
238
+
239
+ type ExcelType = "str" | "inlineStr" | "b" | "n";
240
+ /** A single cell. Mirrors PHP `Workbook\Cell`. */
241
+ declare class Cell {
242
+ readonly address: string;
243
+ readonly value: CellPrimitive;
244
+ readonly formula: string | null;
245
+ readonly format: CellFormat | null;
246
+ readonly comment: CellComment | null;
247
+ readonly cachedValue: CellPrimitive;
248
+ constructor(address: string, value: CellPrimitive, formula?: string | null, format?: CellFormat | null, comment?: CellComment | null, cachedValue?: CellPrimitive);
249
+ excelType(): ExcelType;
250
+ }
251
+
252
+ declare class MergedRegion {
253
+ readonly start: string;
254
+ readonly end: string;
255
+ constructor(start: string, end: string);
256
+ ref(): string;
257
+ }
258
+
259
+ /** A worksheet. Mirrors PHP `Workbook\Sheet`. Cells are an A1-keyed map. */
260
+ declare class Sheet {
261
+ readonly name: string;
262
+ readonly cells: Map<string, Cell>;
263
+ readonly mergedRegions: MergedRegion[];
264
+ readonly columnWidths: Map<number, number>;
265
+ readonly frozenRows: number;
266
+ readonly frozenCols: number;
267
+ constructor(name: string, cells?: Map<string, Cell>, mergedRegions?: MergedRegion[], columnWidths?: Map<number, number>, frozenRows?: number, frozenCols?: number);
268
+ /** rowNumber → (colLetter → Cell), sorted by ascending row number. */
269
+ rows(): Map<number, Map<string, Cell>>;
270
+ hasComments(): boolean;
271
+ comments(): {
272
+ address: string;
273
+ comment: CellComment;
274
+ }[];
275
+ }
276
+
277
+ /** Internal canonical workbook value object. Mirrors PHP `Workbook\Workbook`. */
278
+ declare class Workbook {
279
+ readonly sheets: Sheet[];
280
+ readonly meta: Record<string, unknown>;
281
+ constructor(sheets: Sheet[], meta?: Record<string, unknown>);
282
+ }
283
+
284
+ type Any$1 = any;
285
+ /** Schema → canonical Workbook. Mirrors PHP `Schema\Normalizer`. */
286
+ declare class Normalizer {
287
+ normalize(schema: Any$1): Workbook;
288
+ private normalizeSheet;
289
+ private normalizeCellMap;
290
+ private normalizeMerges;
291
+ private normalizeColumnWidths;
292
+ private columnFormat;
293
+ private buildCell;
294
+ private coerceValue;
295
+ }
296
+
297
+ /**
298
+ * Evaluates every formula and reports Excel-style errors. Mirrors PHP
299
+ * `Schema\FormulaLinter` rule-for-rule.
300
+ */
301
+ declare class FormulaLinter {
302
+ private index;
303
+ private cache;
304
+ lint(schema: unknown): FormulaProblem[];
305
+ private buildIndex;
306
+ private isError;
307
+ private evaluate;
308
+ private tokenize;
309
+ private peek;
310
+ private isOp;
311
+ private parseExpr;
312
+ private parseConcat;
313
+ private parseArith;
314
+ private parseTerm;
315
+ private parseUnary;
316
+ private parsePrimary;
317
+ private resolveRefOrRange;
318
+ private cleanRef;
319
+ private cleanSheetName;
320
+ private resolveCell;
321
+ private resolveRange;
322
+ private expectOp;
323
+ private coerceNumber;
324
+ private coerceString;
325
+ private compare;
326
+ private cmpVal;
327
+ private callFunction;
328
+ private flatten;
329
+ private isNumericLike;
330
+ private maybeNum;
331
+ private avg;
332
+ private minMax;
333
+ private ifFn;
334
+ private hint;
335
+ private hintValue;
336
+ }
337
+
338
+ declare const Inference: {
339
+ detect(columnValues: unknown[], headerName: string, options?: BuilderOptions): ColumnSchema;
340
+ };
341
+
342
+ /** Theme presets — pre-baked CellFormat sets. Mirrors PHP `Schema\Theme`. */
343
+ declare class Theme {
344
+ readonly key: string;
345
+ constructor(key: string);
346
+ headerFormat(): CellFormat | null;
347
+ dataFormat(rowIndexZeroBased: number): CellFormat | null;
348
+ totalsFormat(): CellFormat | null;
349
+ }
350
+
351
+ /**
352
+ * XLSX writer — emits a complete OOXML SpreadsheetML package as bytes.
353
+ * Mirrors PHP `Writer\XlsxWriter` (file I/O moved to the Agent for isomorphism).
354
+ */
355
+ declare class XlsxWriter {
356
+ toBytes(workbook: Workbook): Uint8Array;
357
+ private contentTypesXml;
358
+ private rootRelsXml;
359
+ private workbookXml;
360
+ private workbookRelsXml;
361
+ private sheetRelsXml;
362
+ private sheetXml;
363
+ private cellXml;
364
+ private commentsXml;
365
+ private vmlDrawingXml;
366
+ private coreXml;
367
+ private appXml;
368
+ private escape;
369
+ }
370
+
371
+ /** XLSX reader — bytes → Holy Sheet schema. Mirrors PHP `Reader\XlsxReader`. */
372
+ declare class XlsxReader {
373
+ describe(bytes: Uint8Array): Record<string, unknown>;
374
+ readWorkbook(bytes: Uint8Array): Workbook;
375
+ private parseDocProps;
376
+ private workbookToSchema;
377
+ private sheetToSchema;
378
+ private cellToSchema;
379
+ }
380
+
381
+ type Any = any;
382
+ /**
383
+ * Flat rows (+ optional headers) → Holy Sheet schema with inferred column types.
384
+ * Mirrors PHP `Helpers\ArrayBuilder`.
385
+ */
386
+ declare const ArrayBuilder: {
387
+ build(rows: Any[][], headers?: string[] | null, sheetName?: string, options?: BuilderOptions): HolySheetSchema;
388
+ };
389
+
390
+ /**
391
+ * CSV string → Holy Sheet schema. Mirrors PHP `Helpers\CsvBuilder`, but takes
392
+ * CSV *content* (isomorphic). To convert a file in Node, read it yourself and
393
+ * pass the string. First row is treated as headers.
394
+ */
395
+ declare const CsvBuilder: {
396
+ build(csv: string, options?: BuilderOptions): HolySheetSchema;
397
+ };
398
+
399
+ /**
400
+ * A1 cell address utilities — column-letter ↔ 0-based index conversion,
401
+ * address parsing. Mirrors PHP `Workbook\CellAddress`.
402
+ */
403
+ declare const CellAddress: {
404
+ /** 0-based column index → Excel-style letters. */
405
+ letter(index: number): string;
406
+ /** Column-letters → 0-based index. */
407
+ index(letters: string): number;
408
+ /** Parse an A1 address into [columnIndex, rowNumber] (1-based row), or null. */
409
+ parse(address: string): [number, number] | null;
410
+ };
411
+
412
+ interface ZipFile {
413
+ name: string;
414
+ data: Uint8Array;
415
+ }
416
+ declare function zipSync(files: ZipFile[]): Uint8Array;
417
+
418
+ declare function unzipSync(data: Uint8Array): Record<string, Uint8Array>;
419
+
420
+ export { Agent, type AggOp, ArrayBuilder, type BuilderOptions, CellAddress, type CellData, type CellFormatInput, type CellPrimitive, type ColumnSchema, type ColumnType, type CommentInput, CsvBuilder, type DisplayFormat, FormulaLinter, type FormulaProblem, HolySheet, type HolySheetSchema, Inference, Normalizer, type RepairResult, Repairer, type RowCell, SchemaException, type SheetSchema, Theme, type ThemeKey, VERSION, type ValidationError, Validator, type WriteResult, XlsxReader, XlsxWriter, type ZipFile, unzipSync, zipSync };