@justybase/spreadsheet-tasks 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.
Files changed (47) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +169 -0
  3. package/dist/BiffReaderWriter.d.ts +44 -0
  4. package/dist/BiffReaderWriter.d.ts.map +1 -0
  5. package/dist/BiffReaderWriter.js +282 -0
  6. package/dist/BiffReaderWriter.js.map +1 -0
  7. package/dist/BigBuffer.d.ts +24 -0
  8. package/dist/BigBuffer.d.ts.map +1 -0
  9. package/dist/BigBuffer.js +120 -0
  10. package/dist/BigBuffer.js.map +1 -0
  11. package/dist/ExcelReaderAbstract.d.ts +17 -0
  12. package/dist/ExcelReaderAbstract.d.ts.map +1 -0
  13. package/dist/ExcelReaderAbstract.js +25 -0
  14. package/dist/ExcelReaderAbstract.js.map +1 -0
  15. package/dist/ReaderFactory.d.ts +6 -0
  16. package/dist/ReaderFactory.d.ts.map +1 -0
  17. package/dist/ReaderFactory.js +56 -0
  18. package/dist/ReaderFactory.js.map +1 -0
  19. package/dist/XlsbReader.d.ts +24 -0
  20. package/dist/XlsbReader.d.ts.map +1 -0
  21. package/dist/XlsbReader.js +186 -0
  22. package/dist/XlsbReader.js.map +1 -0
  23. package/dist/XlsbWriter.d.ts +69 -0
  24. package/dist/XlsbWriter.d.ts.map +1 -0
  25. package/dist/XlsbWriter.js +802 -0
  26. package/dist/XlsbWriter.js.map +1 -0
  27. package/dist/XlsxReader.d.ts +30 -0
  28. package/dist/XlsxReader.d.ts.map +1 -0
  29. package/dist/XlsxReader.js +341 -0
  30. package/dist/XlsxReader.js.map +1 -0
  31. package/dist/XlsxWriter.d.ts +31 -0
  32. package/dist/XlsxWriter.d.ts.map +1 -0
  33. package/dist/XlsxWriter.js +415 -0
  34. package/dist/XlsxWriter.js.map +1 -0
  35. package/dist/index.d.ts +9 -0
  36. package/dist/index.d.ts.map +1 -0
  37. package/dist/index.js +23 -0
  38. package/dist/index.js.map +1 -0
  39. package/docs/API.md +271 -0
  40. package/docs/BENCHMARK.md +129 -0
  41. package/docs/PUBLISHING.md +89 -0
  42. package/examples/basic-read.ts +109 -0
  43. package/examples/basic-write.ts +84 -0
  44. package/examples/large-dataset.ts +216 -0
  45. package/examples/multiple-sheets.ts +126 -0
  46. package/examples/streaming-example.ts +181 -0
  47. package/package.json +70 -0
@@ -0,0 +1,216 @@
1
+ /**
2
+ * Large Dataset Example
3
+ *
4
+ * This example demonstrates how to efficiently handle large datasets
5
+ * using spreadsheet-tasks. It shows the performance benefits of XLSB format.
6
+ *
7
+ * Run with: npx ts-node examples/large-dataset.ts
8
+ */
9
+
10
+ import { XlsbWriter, XlsxWriter, XlsbReader, XlsxReader } from '../dist';
11
+ import * as path from 'path';
12
+ import * as fs from 'fs';
13
+
14
+ // Ensure output directory exists
15
+ const outputDir = path.join(__dirname, 'output');
16
+ if (!fs.existsSync(outputDir)) {
17
+ fs.mkdirSync(outputDir, { recursive: true });
18
+ }
19
+
20
+ // Configuration
21
+ const ROW_COUNT = 100000; // 100K rows
22
+
23
+ /**
24
+ * Generate test data with various data types
25
+ */
26
+ function generateTestData(rowCount: number): any[][] {
27
+ const data: any[][] = [];
28
+
29
+ // Headers
30
+ data.push(['ID', 'Name', 'Email', 'Amount', 'Date', 'Active', 'Score']);
31
+
32
+ const names = ['Alice', 'Bob', 'Charlie', 'Diana', 'Eve', 'Frank', 'Grace', 'Henry'];
33
+ const domains = ['gmail.com', 'yahoo.com', 'outlook.com', 'company.com'];
34
+
35
+ for (let i = 0; i < rowCount; i++) {
36
+ const name = names[i % names.length];
37
+ const domain = domains[i % domains.length];
38
+
39
+ data.push([
40
+ i + 1, // ID (number)
41
+ `${name} ${i}`, // Name (string)
42
+ `${name.toLowerCase()}${i}@${domain}`, // Email (string)
43
+ Math.round(Math.random() * 10000 * 100) / 100, // Amount (decimal)
44
+ new Date(2020, i % 12, (i % 28) + 1), // Date
45
+ i % 3 !== 0, // Active (boolean)
46
+ Math.floor(Math.random() * 100), // Score (integer)
47
+ ]);
48
+ }
49
+
50
+ return data;
51
+ }
52
+
53
+ /**
54
+ * Write large dataset to XLSB file
55
+ */
56
+ async function writeLargeXlsb(data: any[][]): Promise<{ time: number; size: number }> {
57
+ const filePath = path.join(outputDir, 'large-dataset.xlsb');
58
+
59
+ const startTime = performance.now();
60
+
61
+ const writer = new XlsbWriter(filePath);
62
+ writer.addSheet('Data');
63
+ writer.writeSheet(data);
64
+ await writer.finalize();
65
+
66
+ const endTime = performance.now();
67
+ const stats = fs.statSync(filePath);
68
+
69
+ return {
70
+ time: endTime - startTime,
71
+ size: stats.size,
72
+ };
73
+ }
74
+
75
+ /**
76
+ * Write large dataset to XLSX file
77
+ */
78
+ async function writeLargeXlsx(data: any[][]): Promise<{ time: number; size: number }> {
79
+ const filePath = path.join(outputDir, 'large-dataset.xlsx');
80
+
81
+ const startTime = performance.now();
82
+
83
+ const writer = new XlsxWriter(filePath);
84
+ writer.addSheet('Data');
85
+ writer.writeSheet(data);
86
+ await writer.finalize();
87
+
88
+ const endTime = performance.now();
89
+ const stats = fs.statSync(filePath);
90
+
91
+ return {
92
+ time: endTime - startTime,
93
+ size: stats.size,
94
+ };
95
+ }
96
+
97
+ /**
98
+ * Read large XLSB file
99
+ */
100
+ async function readLargeXlsb(): Promise<{ time: number; rowCount: number }> {
101
+ const filePath = path.join(outputDir, 'large-dataset.xlsb');
102
+
103
+ const startTime = performance.now();
104
+
105
+ const reader = new XlsbReader();
106
+ await reader.open(filePath);
107
+
108
+ let rowCount = 0;
109
+ while (reader.read()) {
110
+ rowCount++;
111
+ // Access values to simulate real-world usage
112
+ for (let i = 0; i < reader.fieldCount; i++) {
113
+ const _ = reader.getValue(i);
114
+ }
115
+ }
116
+
117
+ const endTime = performance.now();
118
+
119
+ return {
120
+ time: endTime - startTime,
121
+ rowCount,
122
+ };
123
+ }
124
+
125
+ /**
126
+ * Read large XLSX file
127
+ */
128
+ async function readLargeXlsx(): Promise<{ time: number; rowCount: number }> {
129
+ const filePath = path.join(outputDir, 'large-dataset.xlsx');
130
+
131
+ const startTime = performance.now();
132
+
133
+ const reader = new XlsxReader();
134
+ await reader.open(filePath);
135
+
136
+ let rowCount = 0;
137
+ while (await reader.read()) {
138
+ rowCount++;
139
+ // Access values to simulate real-world usage
140
+ for (let i = 0; i < reader.fieldCount; i++) {
141
+ const _ = reader.getValue(i);
142
+ }
143
+ }
144
+
145
+ await reader.close();
146
+ const endTime = performance.now();
147
+
148
+ return {
149
+ time: endTime - startTime,
150
+ rowCount,
151
+ };
152
+ }
153
+
154
+ function formatBytes(bytes: number): string {
155
+ if (bytes < 1024) return `${bytes} B`;
156
+ if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(2)} KB`;
157
+ return `${(bytes / (1024 * 1024)).toFixed(2)} MB`;
158
+ }
159
+
160
+ async function main() {
161
+ console.log('='.repeat(60));
162
+ console.log('Large Dataset Performance Test');
163
+ console.log('='.repeat(60));
164
+ console.log(`Row count: ${ROW_COUNT.toLocaleString()}`);
165
+ console.log('');
166
+
167
+ // Generate test data
168
+ console.log('Generating test data...');
169
+ const data = generateTestData(ROW_COUNT);
170
+ console.log(`Data generated: ${data.length.toLocaleString()} rows\n`);
171
+
172
+ // Write tests
173
+ console.log('--- WRITE TESTS ---\n');
174
+
175
+ console.log('Writing XLSB...');
176
+ const xlsbWrite = await writeLargeXlsb(data);
177
+ console.log(` Time: ${xlsbWrite.time.toFixed(2)} ms`);
178
+ console.log(` Size: ${formatBytes(xlsbWrite.size)}\n`);
179
+
180
+ console.log('Writing XLSX...');
181
+ const xlsxWrite = await writeLargeXlsx(data);
182
+ console.log(` Time: ${xlsxWrite.time.toFixed(2)} ms`);
183
+ console.log(` Size: ${formatBytes(xlsxWrite.size)}\n`);
184
+
185
+ // Read tests
186
+ console.log('--- READ TESTS ---\n');
187
+
188
+ console.log('Reading XLSB...');
189
+ const xlsbRead = await readLargeXlsb();
190
+ console.log(` Time: ${xlsbRead.time.toFixed(2)} ms`);
191
+ console.log(` Rows: ${xlsbRead.rowCount.toLocaleString()}\n`);
192
+
193
+ console.log('Reading XLSX...');
194
+ const xlsxRead = await readLargeXlsx();
195
+ console.log(` Time: ${xlsxRead.time.toFixed(2)} ms`);
196
+ console.log(` Rows: ${xlsxRead.rowCount.toLocaleString()}\n`);
197
+
198
+ // Summary
199
+ console.log('='.repeat(60));
200
+ console.log('SUMMARY');
201
+ console.log('='.repeat(60));
202
+ console.log('');
203
+ console.log('Write Performance:');
204
+ console.log(` XLSB: ${xlsbWrite.time.toFixed(2)} ms (${formatBytes(xlsbWrite.size)})`);
205
+ console.log(` XLSX: ${xlsxWrite.time.toFixed(2)} ms (${formatBytes(xlsxWrite.size)})`);
206
+ console.log(` XLSB is ${(xlsxWrite.time / xlsbWrite.time).toFixed(2)}x faster`);
207
+ console.log(` XLSB is ${((1 - xlsbWrite.size / xlsxWrite.size) * 100).toFixed(0)}% smaller`);
208
+ console.log('');
209
+ console.log('Read Performance:');
210
+ console.log(` XLSB: ${xlsbRead.time.toFixed(2)} ms`);
211
+ console.log(` XLSX: ${xlsxRead.time.toFixed(2)} ms`);
212
+ console.log(` XLSB is ${(xlsxRead.time / xlsbRead.time).toFixed(2)}x faster`);
213
+ console.log('');
214
+ }
215
+
216
+ main().catch(console.error);
@@ -0,0 +1,126 @@
1
+ /**
2
+ * Multiple Sheets Example
3
+ *
4
+ * This example demonstrates how to work with multiple worksheets
5
+ * in a single workbook.
6
+ *
7
+ * Run with: npx ts-node examples/multiple-sheets.ts
8
+ */
9
+
10
+ import { XlsbWriter, XlsxWriter } from '../dist';
11
+ import * as path from 'path';
12
+ import * as fs from 'fs';
13
+
14
+ // Ensure output directory exists
15
+ const outputDir = path.join(__dirname, 'output');
16
+ if (!fs.existsSync(outputDir)) {
17
+ fs.mkdirSync(outputDir, { recursive: true });
18
+ }
19
+
20
+ async function createMultiSheetXlsb() {
21
+ console.log('Creating multi-sheet XLSB file...');
22
+
23
+ const filePath = path.join(outputDir, 'multi-sheet.xlsb');
24
+ const writer = new XlsbWriter(filePath);
25
+
26
+ // Sheet 1: Sales Summary
27
+ writer.addSheet('Sales Summary');
28
+ writer.writeSheet([
29
+ ['Region', 'Q1', 'Q2', 'Q3', 'Q4', 'Total'],
30
+ ['North', 125000, 142000, 138000, 165000, 570000],
31
+ ['South', 98000, 105000, 112000, 128000, 443000],
32
+ ['East', 156000, 167000, 178000, 195000, 696000],
33
+ ['West', 189000, 198000, 205000, 225000, 817000],
34
+ ]);
35
+
36
+ // Sheet 2: Monthly Details
37
+ writer.addSheet('Monthly Details');
38
+ writer.writeSheet([
39
+ ['Month', 'Revenue', 'Expenses', 'Profit'],
40
+ ['January', 45000, 32000, 13000],
41
+ ['February', 52000, 35000, 17000],
42
+ ['March', 48000, 33000, 15000],
43
+ ['April', 55000, 36000, 19000],
44
+ ['May', 61000, 38000, 23000],
45
+ ['June', 58000, 37000, 21000],
46
+ ]);
47
+
48
+ // Sheet 3: Hidden configuration sheet
49
+ writer.addSheet('Config', true); // hidden = true
50
+ writer.writeSheet([
51
+ ['Setting', 'Value'],
52
+ ['Version', '1.0.0'],
53
+ ['LastUpdated', new Date()],
54
+ ['AutoRefresh', true],
55
+ ]);
56
+
57
+ // Sheet 4: Products
58
+ writer.addSheet('Products');
59
+ writer.writeSheet([
60
+ ['SKU', 'Product Name', 'Category', 'Price', 'Stock'],
61
+ ['SKU-001', 'Laptop Pro 15', 'Electronics', 1299.99, 45],
62
+ ['SKU-002', 'Wireless Mouse', 'Accessories', 29.99, 500],
63
+ ['SKU-003', 'USB-C Hub', 'Accessories', 49.99, 200],
64
+ ['SKU-004', 'Monitor 27"', 'Electronics', 399.99, 75],
65
+ ['SKU-005', 'Mechanical Keyboard', 'Accessories', 129.99, 150],
66
+ ]);
67
+
68
+ await writer.finalize();
69
+ console.log(`Created: ${filePath}`);
70
+ console.log('Sheets: Sales Summary, Monthly Details, Config (hidden), Products\n');
71
+ }
72
+
73
+ async function createMultiSheetXlsx() {
74
+ console.log('Creating multi-sheet XLSX file...');
75
+
76
+ const filePath = path.join(outputDir, 'multi-sheet.xlsx');
77
+ const writer = new XlsxWriter(filePath);
78
+
79
+ // Sheet 1: Employees
80
+ writer.addSheet('Employees');
81
+ writer.writeSheet([
82
+ ['ID', 'Name', 'Department', 'Hire Date', 'Salary'],
83
+ [1, 'John Doe', 'Engineering', new Date('2020-01-15'), 85000],
84
+ [2, 'Jane Smith', 'Marketing', new Date('2019-06-01'), 72000],
85
+ [3, 'Bob Johnson', 'Sales', new Date('2021-03-10'), 68000],
86
+ [4, 'Alice Brown', 'HR', new Date('2018-09-22'), 62000],
87
+ [5, 'Charlie Wilson', 'Engineering', new Date('2022-02-28'), 90000],
88
+ ]);
89
+
90
+ // Sheet 2: Departments
91
+ writer.addSheet('Departments');
92
+ writer.writeSheet([
93
+ ['Department', 'Manager', 'Budget', 'Headcount'],
94
+ ['Engineering', 'Sarah Connor', 2500000, 45],
95
+ ['Marketing', 'Mike Ross', 1200000, 22],
96
+ ['Sales', 'Lisa Chen', 1800000, 35],
97
+ ['HR', 'Tom Hardy', 800000, 12],
98
+ ['Finance', 'Emma Watson', 600000, 8],
99
+ ]);
100
+
101
+ // Sheet 3: Projects
102
+ writer.addSheet('Projects');
103
+ writer.writeSheet([
104
+ ['Project Name', 'Status', 'Start Date', 'End Date', 'Budget'],
105
+ ['Website Redesign', 'In Progress', new Date('2024-01-01'), new Date('2024-06-30'), 150000],
106
+ ['Mobile App v2', 'Planning', new Date('2024-04-01'), new Date('2024-12-31'), 300000],
107
+ ['CRM Integration', 'Completed', new Date('2023-06-01'), new Date('2024-01-31'), 200000],
108
+ ['Data Migration', 'On Hold', new Date('2024-03-01'), new Date('2024-09-30'), 100000],
109
+ ]);
110
+
111
+ await writer.finalize();
112
+ console.log(`Created: ${filePath}`);
113
+ console.log('Sheets: Employees, Departments, Projects\n');
114
+ }
115
+
116
+ async function main() {
117
+ try {
118
+ await createMultiSheetXlsb();
119
+ await createMultiSheetXlsx();
120
+ console.log('All multi-sheet files created successfully!');
121
+ } catch (error) {
122
+ console.error('Error:', error);
123
+ }
124
+ }
125
+
126
+ main();
@@ -0,0 +1,181 @@
1
+ /**
2
+ * Streaming Example
3
+ *
4
+ * This example demonstrates how to use the streaming API to write
5
+ * large datasets efficiently without loading all data into memory.
6
+ *
7
+ * Run with: npx ts-node examples/streaming-example.ts
8
+ */
9
+
10
+ import { XlsbWriter } from '../dist/XlsbWriter';
11
+ import * as path from 'path';
12
+
13
+ async function streamingExample() {
14
+ console.log('=== XlsbWriter Streaming Example ===\n');
15
+
16
+ const outputPath = path.join(__dirname, '..', 'output', 'streaming-example.xlsb');
17
+ console.log(`Output file: ${outputPath}\n`);
18
+
19
+ const writer = new XlsbWriter(outputPath);
20
+
21
+ // Example 1: Generate large dataset without loading all into memory
22
+ console.log('Example 1: Generating 100,000 rows using streaming...');
23
+ const startTime1 = Date.now();
24
+ const initialMemory = process.memoryUsage().heapUsed / 1024 / 1024;
25
+
26
+ writer.startSheet('LargeDataset', 5, ['ID', 'Name', 'Value', 'Date', 'Active']);
27
+
28
+ for (let i = 0; i < 100_000; i++) {
29
+ writer.writeRow([
30
+ i + 1,
31
+ `User_${i + 1}`,
32
+ Math.random() * 10000,
33
+ new Date(2024, 0, 1 + (i % 365)),
34
+ i % 2 === 0
35
+ ]);
36
+
37
+ // Log progress every 20,000 rows
38
+ if ((i + 1) % 20_000 === 0) {
39
+ const currentMemory = process.memoryUsage().heapUsed / 1024 / 1024;
40
+ const memoryDelta = (currentMemory - initialMemory).toFixed(2);
41
+ console.log(` Processed ${(i + 1).toLocaleString()} rows | Memory delta: ${memoryDelta} MB`);
42
+ }
43
+ }
44
+
45
+ writer.endSheet();
46
+ const elapsed1 = Date.now() - startTime1;
47
+ const finalMemory = process.memoryUsage().heapUsed / 1024 / 1024;
48
+ const totalMemoryUsed = (finalMemory - initialMemory).toFixed(2);
49
+
50
+ console.log(`✓ Completed in ${elapsed1}ms`);
51
+ console.log(` Total memory delta: ${totalMemoryUsed} MB\n`);
52
+
53
+ // Example 2: Multiple sheets with streaming
54
+ console.log('Example 2: Creating multiple sheets with streaming...');
55
+ const startTime2 = Date.now();
56
+
57
+ // Sheet 2: Customer data
58
+ writer.startSheet('Customers', 4, ['CustomerID', 'Email', 'SignupDate', 'Premium']);
59
+ for (let i = 0; i < 10_000; i++) {
60
+ writer.writeRow([
61
+ 1000 + i,
62
+ `customer${i}@example.com`,
63
+ new Date(2020 + (i % 5), i % 12, (i % 28) + 1),
64
+ i % 3 === 0
65
+ ]);
66
+ }
67
+ writer.endSheet();
68
+
69
+ // Sheet 3: Transactions
70
+ writer.startSheet('Transactions', 3, ['TransactionID', 'Amount', 'Timestamp']);
71
+ for (let i = 0; i < 50_000; i++) {
72
+ writer.writeRow([
73
+ i + 1,
74
+ parseFloat((Math.random() * 5000).toFixed(2)),
75
+ new Date(2024, i % 12, (i % 28) + 1, i % 24, i % 60)
76
+ ]);
77
+ }
78
+ writer.endSheet();
79
+
80
+ const elapsed2 = Date.now() - startTime2;
81
+ console.log(`✓ Multiple sheets completed in ${elapsed2}ms\n`);
82
+
83
+ // Example 3: Mixed data types without autofilter
84
+ console.log('Example 3: Mixed data types (no autofilter)...');
85
+ writer.startSheet('MixedTypes', 6, undefined, { doAutofilter: false });
86
+
87
+ for (let i = 0; i < 1000; i++) {
88
+ writer.writeRow([
89
+ i,
90
+ `Text ${i}`,
91
+ Math.PI * i,
92
+ new Date(),
93
+ i % 2 === 0,
94
+ null // null values are supported
95
+ ]);
96
+ }
97
+ writer.endSheet();
98
+ console.log('✓ Completed\n');
99
+
100
+ // Finalize the workbook
101
+ console.log('Finalizing workbook...');
102
+ await writer.finalize();
103
+ console.log('✓ Done!\n');
104
+
105
+ console.log('=== Summary ===');
106
+ console.log('Total sheets created: 4');
107
+ console.log('Total rows written: ~161,000');
108
+ console.log(`File saved to: ${outputPath}`);
109
+ }
110
+
111
+ // Memory comparison function
112
+ async function compareMemoryUsage() {
113
+ console.log('\n=== Memory Usage Comparison ===\n');
114
+
115
+ const rowCount = 50_000;
116
+ const cols = 5;
117
+
118
+ // Test 1: Streaming mode
119
+ console.log('Test 1: Streaming mode');
120
+ const streamingFile = path.join(__dirname, '..', 'output', 'streaming-test.xlsb');
121
+ const writer1 = new XlsbWriter(streamingFile);
122
+
123
+ const streamStart = Date.now();
124
+ const streamMemStart = process.memoryUsage().heapUsed / 1024 / 1024;
125
+
126
+ writer1.startSheet('Data', cols, ['Col1', 'Col2', 'Col3', 'Col4', 'Col5']);
127
+ for (let i = 0; i < rowCount; i++) {
128
+ writer1.writeRow([i, `Text${i}`, Math.random() * 1000, new Date(), i % 2 === 0]);
129
+ }
130
+ writer1.endSheet();
131
+ await writer1.finalize();
132
+
133
+ const streamEnd = Date.now();
134
+ const streamMemEnd = process.memoryUsage().heapUsed / 1024 / 1024;
135
+ const streamTime = streamEnd - streamStart;
136
+ const streamMem = (streamMemEnd - streamMemStart).toFixed(2);
137
+
138
+ console.log(` Time: ${streamTime}ms`);
139
+ console.log(` Memory delta: ${streamMem} MB\n`);
140
+
141
+ // Test 2: Batch mode (traditional writeSheet)
142
+ console.log('Test 2: Batch mode (traditional writeSheet)');
143
+ const batchFile = path.join(__dirname, '..', 'output', 'batch-test.xlsb');
144
+ const writer2 = new XlsbWriter(batchFile);
145
+
146
+ const batchStart = Date.now();
147
+ const batchMemStart = process.memoryUsage().heapUsed / 1024 / 1024;
148
+
149
+ // Generate all rows in memory first
150
+ const rows: any[][] = [];
151
+ for (let i = 0; i < rowCount; i++) {
152
+ rows.push([i, `Text${i}`, Math.random() * 1000, new Date(), i % 2 === 0]);
153
+ }
154
+
155
+ writer2.addSheet('Data');
156
+ writer2.writeSheet(rows, ['Col1', 'Col2', 'Col3', 'Col4', 'Col5']);
157
+ await writer2.finalize();
158
+
159
+ const batchEnd = Date.now();
160
+ const batchMemEnd = process.memoryUsage().heapUsed / 1024 / 1024;
161
+ const batchTime = batchEnd - batchStart;
162
+ const batchMem = (batchMemEnd - batchMemStart).toFixed(2);
163
+
164
+ console.log(` Time: ${batchTime}ms`);
165
+ console.log(` Memory delta: ${batchMem} MB\n`);
166
+
167
+ console.log('=== Results ===');
168
+ console.log(`Streaming is ${(parseFloat(batchMem) / parseFloat(streamMem)).toFixed(1)}x more memory efficient`);
169
+ console.log(`Speed difference: ${Math.abs(streamTime - batchTime)}ms ${streamTime < batchTime ? 'faster' : 'slower'}`);
170
+ }
171
+
172
+ // Run examples
173
+ (async () => {
174
+ try {
175
+ await streamingExample();
176
+ await compareMemoryUsage();
177
+ } catch (error) {
178
+ console.error('Error:', error);
179
+ process.exit(1);
180
+ }
181
+ })();
package/package.json ADDED
@@ -0,0 +1,70 @@
1
+ {
2
+ "name": "@justybase/spreadsheet-tasks",
3
+ "version": "1.0.0",
4
+ "description": "High-performance TypeScript library for reading and writing Excel files in XLSB and XLSX formats. XLSB is 3.3x faster to write and 2.1x faster to read than XLSX.",
5
+ "main": "dist/index.js",
6
+ "types": "dist/index.d.ts",
7
+ "files": [
8
+ "dist",
9
+ "README.md",
10
+ "LICENSE",
11
+ "docs",
12
+ "examples"
13
+ ],
14
+ "scripts": {
15
+ "build": "tsc",
16
+ "lint": "eslint src/",
17
+ "typecheck": "tsc --noEmit",
18
+ "test": "npm run build && npm run test:smoke && npm run test:unit && npm run test:integration",
19
+ "test:smoke": "npm run build && npx ts-node tests/smoke.test.ts",
20
+ "test:unit": "npx ts-node tests/unit/bigbuffer.test.ts && npx ts-node tests/unit/biff-reader-writer.test.ts && npx ts-node tests/unit/xlsb-writer.test.ts",
21
+ "test:integration": "npm run build && npx ts-node tests/integration/xlsb-writer.test.ts && npx ts-node tests/integration/xlsx-writer.test.ts",
22
+ "test:xlsb": "npm run build && npx ts-node tests/integration/xlsb-writer.test.ts",
23
+ "test:xlsx": "npm run build && npx ts-node tests/integration/xlsx-writer.test.ts",
24
+ "benchmark": "npm run build && npx ts-node benchmarks/performance.bench.ts",
25
+ "benchmark:comparison": "npm run build && npx ts-node benchmarks/comparison.bench.ts",
26
+ "prepublishOnly": "npm run build && npm test"
27
+ },
28
+ "keywords": [
29
+ "excel",
30
+ "xlsb",
31
+ "xlsx",
32
+ "spreadsheet",
33
+ "binary",
34
+ "workbook",
35
+ "reader",
36
+ "writer",
37
+ "typescript",
38
+ "performance"
39
+ ],
40
+ "author": "Krzysztof Dusko",
41
+ "license": "MIT",
42
+ "repository": {
43
+ "type": "git",
44
+ "url": "git+https://github.com/KrzysztofDusko/XlsbWriterNode.git"
45
+ },
46
+ "homepage": "https://github.com/KrzysztofDusko/XlsbWriterNode#readme",
47
+ "bugs": {
48
+ "url": "https://github.com/KrzysztofDusko/XlsbWriterNode/issues"
49
+ },
50
+ "engines": {
51
+ "node": ">=16.0.0"
52
+ },
53
+ "dependencies": {
54
+ "adm-zip": "^0.5.16",
55
+ "archiver": "^7.0.1",
56
+ "yauzl": "^3.2.0"
57
+ },
58
+ "devDependencies": {
59
+ "@eslint/js": "^9.17.0",
60
+ "@types/adm-zip": "^0.5.6",
61
+ "@types/archiver": "^7.0.0",
62
+ "@types/node": "^22.10.5",
63
+ "@types/yauzl": "^2.10.3",
64
+ "eslint": "^9.17.0",
65
+ "exceljs": "^4.4.0",
66
+ "ts-node": "^10.9.2",
67
+ "typescript": "^5.7.2",
68
+ "typescript-eslint": "^8.19.1"
69
+ }
70
+ }