rowpipe 1.0.0 → 1.1.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 (106) hide show
  1. package/README.md +25 -32
  2. package/dist/cli/index.js +4 -4
  3. package/dist/cli/index.js.map +1 -1
  4. package/dist/core/types.d.ts +2 -0
  5. package/dist/core/types.d.ts.map +1 -1
  6. package/dist/index.d.ts +2 -2
  7. package/dist/index.d.ts.map +1 -1
  8. package/dist/index.js +2 -2
  9. package/dist/index.js.map +1 -1
  10. package/dist/readers/csv.d.ts.map +1 -1
  11. package/dist/readers/csv.js +28 -16
  12. package/dist/readers/csv.js.map +1 -1
  13. package/dist/readers/index.d.ts +1 -0
  14. package/dist/readers/index.d.ts.map +1 -1
  15. package/dist/readers/index.js +29 -3
  16. package/dist/readers/index.js.map +1 -1
  17. package/dist/readers/json.d.ts.map +1 -1
  18. package/dist/readers/json.js +6 -8
  19. package/dist/readers/json.js.map +1 -1
  20. package/dist/readers/jsonl.d.ts.map +1 -1
  21. package/dist/readers/jsonl.js +5 -7
  22. package/dist/readers/jsonl.js.map +1 -1
  23. package/dist/readers/parquet.d.ts +17 -0
  24. package/dist/readers/parquet.d.ts.map +1 -0
  25. package/dist/readers/parquet.js +146 -0
  26. package/dist/readers/parquet.js.map +1 -0
  27. package/dist/utils/compression.d.ts +30 -6
  28. package/dist/utils/compression.d.ts.map +1 -1
  29. package/dist/utils/compression.js +95 -18
  30. package/dist/utils/compression.js.map +1 -1
  31. package/dist/writers/csv.d.ts.map +1 -1
  32. package/dist/writers/csv.js +9 -11
  33. package/dist/writers/csv.js.map +1 -1
  34. package/dist/writers/index.d.ts +2 -0
  35. package/dist/writers/index.d.ts.map +1 -1
  36. package/dist/writers/index.js +49 -4
  37. package/dist/writers/index.js.map +1 -1
  38. package/dist/writers/json.d.ts +1 -1
  39. package/dist/writers/json.d.ts.map +1 -1
  40. package/dist/writers/json.js +9 -11
  41. package/dist/writers/json.js.map +1 -1
  42. package/dist/writers/jsonl.d.ts +1 -1
  43. package/dist/writers/jsonl.d.ts.map +1 -1
  44. package/dist/writers/jsonl.js +9 -11
  45. package/dist/writers/jsonl.js.map +1 -1
  46. package/dist/writers/markdown.d.ts +21 -0
  47. package/dist/writers/markdown.d.ts.map +1 -0
  48. package/dist/writers/markdown.js +82 -0
  49. package/dist/writers/markdown.js.map +1 -0
  50. package/dist/writers/parquet.d.ts +19 -0
  51. package/dist/writers/parquet.d.ts.map +1 -0
  52. package/dist/writers/parquet.js +129 -0
  53. package/dist/writers/parquet.js.map +1 -0
  54. package/package.json +13 -2
  55. package/skills/rowpipe/SKILL.md +181 -0
  56. package/benchmarks/memory-bench.ts +0 -109
  57. package/src/analytics/reduce.ts +0 -388
  58. package/src/analytics/schema-inference.ts +0 -217
  59. package/src/analytics/semantic-types.ts +0 -36
  60. package/src/analytics/stats.ts +0 -383
  61. package/src/analytics/validator.ts +0 -134
  62. package/src/cli/commands/cast.ts +0 -60
  63. package/src/cli/commands/convert.ts +0 -128
  64. package/src/cli/commands/filter.ts +0 -58
  65. package/src/cli/commands/inspect.ts +0 -193
  66. package/src/cli/commands/map.ts +0 -66
  67. package/src/cli/commands/reduce.ts +0 -74
  68. package/src/cli/commands/rename.ts +0 -59
  69. package/src/cli/commands/sample.ts +0 -61
  70. package/src/cli/commands/schema.ts +0 -86
  71. package/src/cli/commands/select.ts +0 -59
  72. package/src/cli/commands/stats.ts +0 -100
  73. package/src/cli/commands/validate.ts +0 -123
  74. package/src/cli/index.ts +0 -285
  75. package/src/core/batch.ts +0 -81
  76. package/src/core/errors.ts +0 -81
  77. package/src/core/pipeline.ts +0 -150
  78. package/src/core/types.ts +0 -110
  79. package/src/index.ts +0 -52
  80. package/src/readers/csv.ts +0 -302
  81. package/src/readers/index.ts +0 -88
  82. package/src/readers/json.ts +0 -256
  83. package/src/readers/jsonl.ts +0 -126
  84. package/src/readers/xlsx.ts +0 -182
  85. package/src/transforms/cast.ts +0 -212
  86. package/src/transforms/expression.ts +0 -1114
  87. package/src/transforms/filter.ts +0 -38
  88. package/src/transforms/map.ts +0 -99
  89. package/src/transforms/rename.ts +0 -47
  90. package/src/transforms/sample.ts +0 -57
  91. package/src/transforms/select.ts +0 -64
  92. package/src/utils/compression.ts +0 -43
  93. package/src/utils/formatting.ts +0 -75
  94. package/src/utils/progress.ts +0 -37
  95. package/src/writers/csv.ts +0 -106
  96. package/src/writers/index.ts +0 -87
  97. package/src/writers/json.ts +0 -52
  98. package/src/writers/jsonl.ts +0 -49
  99. package/src/writers/xlsx.ts +0 -87
  100. package/tests/analytics.test.ts +0 -119
  101. package/tests/cli-integration.test.ts +0 -187
  102. package/tests/map-reduce.test.ts +0 -223
  103. package/tests/readers-writers.test.ts +0 -189
  104. package/tests/transforms.test.ts +0 -199
  105. package/tsconfig.json +0 -21
  106. package/vitest.config.ts +0 -9
@@ -1,128 +0,0 @@
1
- import { mkdir } from "node:fs/promises";
2
- import { join } from "node:path";
3
- import { createPipeline } from "../../core/pipeline.js";
4
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
5
- import { XLSXReader } from "../../readers/xlsx.js";
6
- import { createWriter, inferFormatFromPath as inferWriterFormat } from "../../writers/index.js";
7
- import { openReadableStream, openWritableStream } from "../../utils/compression.js";
8
- import { formatNumber, logMemoryDebug } from "../../utils/formatting.js";
9
- import { ProgressReporter } from "../../utils/progress.js";
10
-
11
- export interface ConvertCommandOptions {
12
- from?: string;
13
- to?: string;
14
- sheet?: string;
15
- allSheets?: boolean;
16
- outDir?: string;
17
- path?: string;
18
- delimiter?: string;
19
- header?: boolean;
20
- batchSize?: string | number;
21
- quiet?: boolean;
22
- noProgress?: boolean;
23
- }
24
-
25
- export async function convertCommand(
26
- inputPath = "-",
27
- outputPath?: string,
28
- options: ConvertCommandOptions = {}
29
- ): Promise<void> {
30
- const effectiveBatchSize = Number(options.batchSize) || 1000;
31
-
32
- // Determine input format
33
- let fromFormat = options.from?.toLowerCase();
34
- if (!fromFormat && inputPath !== "-") {
35
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
36
- }
37
- if (!fromFormat) {
38
- fromFormat = "csv";
39
- }
40
-
41
- // Handle multi-sheet export if --all-sheets is specified
42
- if (options.allSheets && fromFormat === "xlsx" && inputPath !== "-") {
43
- const outDir = options.outDir || outputPath || "./";
44
- const toFormat = (options.to?.toLowerCase() || "csv").replace(/^\./, "");
45
-
46
- await mkdir(outDir, { recursive: true });
47
-
48
- const xlsxReader = new XLSXReader(inputPath);
49
- const sheets = await xlsxReader.getParsedSheets();
50
-
51
- if (sheets.length === 0) {
52
- process.stderr.write("No sheets found in workbook.\n");
53
- return;
54
- }
55
-
56
- process.stderr.write(`Exporting ${sheets.length} sheets to "${outDir}"...\n`);
57
-
58
- for (const sheet of sheets) {
59
- const sheetName = sheet.sheet;
60
- const targetFileName = `${sheetName}.${toFormat}`;
61
- const targetFilePath = join(outDir, targetFileName);
62
-
63
- const sheetReader = createReader(inputPath, {
64
- format: "xlsx",
65
- sheet: sheetName,
66
- batchSize: effectiveBatchSize,
67
- filePath: inputPath,
68
- });
69
-
70
- const sheetWriter = createWriter(targetFilePath, {
71
- format: toFormat,
72
- delimiter: options.delimiter,
73
- header: options.header,
74
- });
75
-
76
- const pipeline = createPipeline(sheetReader, { batchSize: effectiveBatchSize });
77
- await pipeline.to(sheetWriter);
78
-
79
- const rowCount = Math.max(0, sheet.data.length - 1);
80
- process.stderr.write(
81
- ` ✓ Sheet "${sheetName}" -> ${targetFilePath} (${formatNumber(rowCount)} rows)\n`
82
- );
83
- }
84
-
85
- process.stderr.write("Done.\n");
86
- logMemoryDebug();
87
- return;
88
- }
89
-
90
- // Determine output format
91
- let toFormat = options.to?.toLowerCase();
92
- if (!toFormat && outputPath && outputPath !== "-") {
93
- toFormat = inferWriterFormat(outputPath) ?? undefined;
94
- }
95
- if (!toFormat) {
96
- toFormat = "csv";
97
- }
98
-
99
- const progress = new ProgressReporter(options);
100
- const effectiveOutput = outputPath || "-";
101
-
102
- const inputStream = openReadableStream(inputPath);
103
- const outputStream = openWritableStream(effectiveOutput);
104
-
105
- const reader = createReader(inputStream, {
106
- format: fromFormat,
107
- sheet: options.sheet,
108
- path: options.path,
109
- delimiter: options.delimiter,
110
- header: options.header,
111
- batchSize: effectiveBatchSize,
112
- filePath: inputPath,
113
- });
114
-
115
- const writer = createWriter(outputStream, {
116
- format: toFormat,
117
- delimiter: options.delimiter,
118
- header: options.header,
119
- sheet: options.sheet,
120
- });
121
-
122
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
123
- pipeline.onProgress((info) => progress.update(info));
124
-
125
- await pipeline.to(writer);
126
- progress.done();
127
- logMemoryDebug();
128
- }
@@ -1,58 +0,0 @@
1
- import { createPipeline } from "../../core/pipeline.js";
2
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
3
- import { createWriter } from "../../writers/index.js";
4
- import { filterRows } from "../../transforms/filter.js";
5
- import { openReadableStream } from "../../utils/compression.js";
6
- import { logMemoryDebug } from "../../utils/formatting.js";
7
- import { ProgressReporter } from "../../utils/progress.js";
8
-
9
- export interface FilterCommandOptions {
10
- from?: string;
11
- to?: string;
12
- sheet?: string;
13
- delimiter?: string;
14
- batchSize?: string | number;
15
- quiet?: boolean;
16
- noProgress?: boolean;
17
- }
18
-
19
- export async function filterCommand(
20
- inputPath = "-",
21
- expression: string,
22
- options: FilterCommandOptions = {}
23
- ): Promise<void> {
24
- const effectiveBatchSize = Number(options.batchSize) || 1000;
25
- const progress = new ProgressReporter(options);
26
-
27
- let fromFormat = options.from?.toLowerCase();
28
- if (!fromFormat && inputPath !== "-") {
29
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
30
- }
31
- if (!fromFormat) {
32
- fromFormat = "csv";
33
- }
34
-
35
- const toFormat = options.to?.toLowerCase() || (fromFormat === "xlsx" ? "csv" : fromFormat);
36
-
37
- const inputStream = openReadableStream(inputPath);
38
- const reader = createReader(inputStream, {
39
- format: fromFormat,
40
- sheet: options.sheet,
41
- delimiter: options.delimiter,
42
- batchSize: effectiveBatchSize,
43
- filePath: inputPath,
44
- });
45
-
46
- const writer = createWriter(process.stdout, {
47
- format: toFormat,
48
- delimiter: options.delimiter,
49
- });
50
-
51
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
52
- pipeline.pipe(filterRows(expression));
53
- pipeline.onProgress((info) => progress.update(info));
54
-
55
- await pipeline.to(writer);
56
- progress.done();
57
- logMemoryDebug();
58
- }
@@ -1,193 +0,0 @@
1
- import { stat } from "node:fs/promises";
2
- import { DatasetStatsAggregator } from "../../analytics/stats.js";
3
- import { SchemaInferenceAggregator } from "../../analytics/schema-inference.js";
4
- import { InvalidArgumentError } from "../../core/errors.js";
5
- import { createPipeline } from "../../core/pipeline.js";
6
- import { createReader, inferFormatFromPath } from "../../readers/index.js";
7
- import { openReadableStream } from "../../utils/compression.js";
8
- import {
9
- formatBytes,
10
- formatDecimal,
11
- formatNumber,
12
- formatTable,
13
- logMemoryDebug,
14
- } from "../../utils/formatting.js";
15
- import { ProgressReporter } from "../../utils/progress.js";
16
-
17
- export interface InspectCommandOptions {
18
- sheet?: string;
19
- path?: string;
20
- delimiter?: string;
21
- json?: boolean;
22
- quiet?: boolean;
23
- noProgress?: boolean;
24
- }
25
-
26
- export async function inspectCommand(
27
- inputPath = "-",
28
- options: InspectCommandOptions = {}
29
- ): Promise<void> {
30
- const progress = new ProgressReporter(options);
31
-
32
- let fileSize: number | undefined;
33
- if (inputPath !== "-") {
34
- try {
35
- const fileStat = await stat(inputPath);
36
- fileSize = fileStat.size;
37
- } catch {
38
- // Ignore if cannot stat
39
- }
40
- }
41
-
42
- const format =
43
- inputPath !== "-" ? inferFormatFromPath(inputPath) || "CSV" : "CSV";
44
-
45
- const stream = openReadableStream(inputPath);
46
- const reader = createReader(stream, {
47
- format,
48
- sheet: options.sheet,
49
- path: options.path,
50
- delimiter: options.delimiter,
51
- filePath: inputPath,
52
- });
53
-
54
- // If XLSX without a specific --sheet requested, show rich workbook & sheet breakdown
55
- if (format === "xlsx" && !options.sheet && reader.inspect) {
56
- const meta = await reader.inspect();
57
- if (options.json) {
58
- process.stdout.write(
59
- JSON.stringify(
60
- {
61
- file: inputPath === "-" ? "stdin" : inputPath,
62
- format: "XLSX",
63
- sizeBytes: fileSize,
64
- sizeFormatted: fileSize !== undefined ? formatBytes(fileSize) : undefined,
65
- sheetsCount: meta.sheets?.length ?? 0,
66
- sheets: meta.sheets,
67
- },
68
- null,
69
- 2
70
- ) + "\n"
71
- );
72
- logMemoryDebug();
73
- return;
74
- }
75
-
76
- process.stdout.write(`File: ${inputPath === "-" ? "stdin" : inputPath}\n`);
77
- process.stdout.write(`Format: XLSX\n`);
78
- if (fileSize !== undefined) {
79
- process.stdout.write(`Size: ${formatBytes(fileSize)}\n`);
80
- }
81
-
82
- if (meta.sheets && meta.sheets.length > 0) {
83
- process.stdout.write(`Sheets: ${meta.sheets.length}\n\n`);
84
- const sheetRows = meta.sheets.map((s) => {
85
- const previewCols = (s.columns || []).slice(0, 5).join(", ") + (s.columns && s.columns.length > 5 ? ", ..." : "");
86
- return [
87
- s.name,
88
- formatNumber(s.rowCount),
89
- s.columnCount !== undefined ? String(s.columnCount) : "-",
90
- previewCols,
91
- ];
92
- });
93
-
94
- process.stdout.write(
95
- formatTable(
96
- ["SHEET", "ROWS", "COLUMNS", "PREVIEW COLUMNS"],
97
- sheetRows,
98
- ["left", "right", "right", "left"]
99
- ) + "\n\nTip: Run with --sheet <name> to inspect a specific sheet in full detail.\n"
100
- );
101
- }
102
- logMemoryDebug();
103
- return;
104
- }
105
-
106
- // General inspection across stream
107
- const schemaAgg = new SchemaInferenceAggregator();
108
- const statsAgg = new DatasetStatsAggregator();
109
-
110
- const pipeline = createPipeline(reader);
111
- pipeline.onProgress((info) => progress.update(info));
112
-
113
- for await (const row of pipeline.rows()) {
114
- schemaAgg.add(row);
115
- statsAgg.add(row);
116
- }
117
-
118
- progress.done();
119
-
120
- const schemaRes = schemaAgg.result();
121
- const statsRes = statsAgg.result();
122
-
123
- const totalRows = schemaRes.totalRowsScanned;
124
- const columnCount = schemaRes.columns.length;
125
-
126
- const columnDetails = schemaRes.columns.map((col) => {
127
- const nullPct =
128
- col.sampleCount > 0 ? (col.nullCount / col.sampleCount) * 100 : 0;
129
- const colStats = statsRes.columns[col.name];
130
- const distinctCount =
131
- colStats?.numeric?.approxDistinct ?? colStats?.string?.approxDistinct ?? 0;
132
- const uniquePct =
133
- totalRows > 0 ? Math.min(100, (distinctCount / totalRows) * 100) : 0;
134
-
135
- return {
136
- name: col.name,
137
- type: col.type,
138
- nullPct,
139
- uniquePct,
140
- semantic: col.semantic,
141
- };
142
- });
143
-
144
- if (options.json) {
145
- const resultJson = {
146
- file: inputPath === "-" ? "stdin" : inputPath,
147
- format: format.toUpperCase(),
148
- sheet: options.sheet,
149
- sizeBytes: fileSize,
150
- sizeFormatted: fileSize !== undefined ? formatBytes(fileSize) : undefined,
151
- rows: totalRows,
152
- columnsCount: columnCount,
153
- columns: columnDetails.map((c) => ({
154
- name: c.name,
155
- type: c.type,
156
- nullPercentage: Math.round(c.nullPct * 10) / 10,
157
- approxUniquePercentage: Math.round(c.uniquePct * 10) / 10,
158
- semantic: c.semantic,
159
- })),
160
- };
161
- process.stdout.write(JSON.stringify(resultJson, null, 2) + "\n");
162
- } else {
163
- process.stdout.write(`File: ${inputPath === "-" ? "stdin" : inputPath}\n`);
164
- process.stdout.write(`Format: ${format.toUpperCase()}`);
165
- if (options.sheet) {
166
- process.stdout.write(` (Sheet: ${options.sheet})`);
167
- }
168
- process.stdout.write("\n");
169
-
170
- if (fileSize !== undefined) {
171
- process.stdout.write(`Size: ${formatBytes(fileSize)}\n`);
172
- }
173
- process.stdout.write(`Rows: ${formatNumber(totalRows)}\n`);
174
- process.stdout.write(`Columns: ${columnCount}\n\n`);
175
-
176
- const tableRows = columnDetails.map((c) => [
177
- c.name,
178
- c.type,
179
- `${formatDecimal(c.nullPct, 1)}%`,
180
- `${formatDecimal(c.uniquePct, 1)}%`,
181
- ]);
182
-
183
- process.stdout.write(
184
- formatTable(
185
- ["COLUMN", "TYPE", "NULL", "UNIQUE*"],
186
- tableRows,
187
- ["left", "left", "right", "right"]
188
- ) + "\n\n* approximate\n"
189
- );
190
- }
191
-
192
- logMemoryDebug();
193
- }
@@ -1,66 +0,0 @@
1
- import { InvalidArgumentError } from "../../core/errors.js";
2
- import { createPipeline } from "../../core/pipeline.js";
3
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
4
- import { createWriter } from "../../writers/index.js";
5
- import { mapRows, parseMapSpecs } from "../../transforms/map.js";
6
- import { openReadableStream } from "../../utils/compression.js";
7
- import { logMemoryDebug } from "../../utils/formatting.js";
8
- import { ProgressReporter } from "../../utils/progress.js";
9
-
10
- export interface MapCommandOptions {
11
- from?: string;
12
- to?: string;
13
- sheet?: string;
14
- delimiter?: string;
15
- batchSize?: string | number;
16
- quiet?: boolean;
17
- noProgress?: boolean;
18
- }
19
-
20
- export async function mapCommand(
21
- inputPath = "-",
22
- specs: string[],
23
- options: MapCommandOptions = {}
24
- ): Promise<void> {
25
- if (!specs || specs.length === 0) {
26
- throw new InvalidArgumentError(
27
- "At least one map specification is required (e.g. rowpipe map users.csv 'full_name=concat(first, \" \", last)')"
28
- );
29
- }
30
-
31
- const effectiveBatchSize = Number(options.batchSize) || 1000;
32
- const progress = new ProgressReporter(options);
33
- const parsedSpecs = parseMapSpecs(specs);
34
-
35
- let fromFormat = options.from?.toLowerCase();
36
- if (!fromFormat && inputPath !== "-") {
37
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
38
- }
39
- if (!fromFormat) {
40
- fromFormat = "csv";
41
- }
42
-
43
- const toFormat = options.to?.toLowerCase() || (fromFormat === "xlsx" ? "csv" : fromFormat);
44
-
45
- const inputStream = openReadableStream(inputPath);
46
- const reader = createReader(inputStream, {
47
- format: fromFormat,
48
- sheet: options.sheet,
49
- delimiter: options.delimiter,
50
- batchSize: effectiveBatchSize,
51
- filePath: inputPath,
52
- });
53
-
54
- const writer = createWriter(process.stdout, {
55
- format: toFormat,
56
- delimiter: options.delimiter,
57
- });
58
-
59
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
60
- pipeline.pipe(mapRows(parsedSpecs));
61
- pipeline.onProgress((info) => progress.update(info));
62
-
63
- await pipeline.to(writer);
64
- progress.done();
65
- logMemoryDebug();
66
- }
@@ -1,74 +0,0 @@
1
- import { InvalidArgumentError } from "../../core/errors.js";
2
- import { createPipeline } from "../../core/pipeline.js";
3
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
4
- import { createWriter } from "../../writers/index.js";
5
- import { parseReduceSpecs, reduceRows } from "../../analytics/reduce.js";
6
- import { openReadableStream } from "../../utils/compression.js";
7
- import { logMemoryDebug } from "../../utils/formatting.js";
8
- import { ProgressReporter } from "../../utils/progress.js";
9
-
10
- export interface ReduceCommandOptions {
11
- by?: string;
12
- from?: string;
13
- to?: string;
14
- sheet?: string;
15
- delimiter?: string;
16
- batchSize?: string | number;
17
- quiet?: boolean;
18
- noProgress?: boolean;
19
- }
20
-
21
- export async function reduceCommand(
22
- inputPath = "-",
23
- specs: string[],
24
- options: ReduceCommandOptions = {}
25
- ): Promise<void> {
26
- if (!specs || specs.length === 0) {
27
- throw new InvalidArgumentError(
28
- "At least one aggregation specification is required (e.g. rowpipe reduce sales.csv 'total=sum(revenue)' --by country)"
29
- );
30
- }
31
-
32
- const effectiveBatchSize = Number(options.batchSize) || 1000;
33
- const progress = new ProgressReporter(options);
34
- const parsedSpecs = parseReduceSpecs(specs);
35
-
36
- const byCols = options.by
37
- ? options.by
38
- .split(",")
39
- .map((c) => c.trim())
40
- .filter(Boolean)
41
- : undefined;
42
-
43
- let fromFormat = options.from?.toLowerCase();
44
- if (!fromFormat && inputPath !== "-") {
45
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
46
- }
47
- if (!fromFormat) {
48
- fromFormat = "csv";
49
- }
50
-
51
- const toFormat = options.to?.toLowerCase() || (fromFormat === "xlsx" ? "csv" : fromFormat);
52
-
53
- const inputStream = openReadableStream(inputPath);
54
- const reader = createReader(inputStream, {
55
- format: fromFormat,
56
- sheet: options.sheet,
57
- delimiter: options.delimiter,
58
- batchSize: effectiveBatchSize,
59
- filePath: inputPath,
60
- });
61
-
62
- const writer = createWriter(process.stdout, {
63
- format: toFormat,
64
- delimiter: options.delimiter,
65
- });
66
-
67
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
68
- pipeline.pipe(reduceRows({ by: byCols, aggregations: parsedSpecs }));
69
- pipeline.onProgress((info) => progress.update(info));
70
-
71
- await pipeline.to(writer);
72
- progress.done();
73
- logMemoryDebug();
74
- }
@@ -1,59 +0,0 @@
1
- import { createPipeline } from "../../core/pipeline.js";
2
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
3
- import { createWriter } from "../../writers/index.js";
4
- import { parseRenameSpecs, renameColumns } from "../../transforms/rename.js";
5
- import { openReadableStream } from "../../utils/compression.js";
6
- import { logMemoryDebug } from "../../utils/formatting.js";
7
- import { ProgressReporter } from "../../utils/progress.js";
8
-
9
- export interface RenameCommandOptions {
10
- from?: string;
11
- to?: string;
12
- sheet?: string;
13
- delimiter?: string;
14
- batchSize?: string | number;
15
- quiet?: boolean;
16
- noProgress?: boolean;
17
- }
18
-
19
- export async function renameCommand(
20
- inputPath = "-",
21
- specs: string[],
22
- options: RenameCommandOptions = {}
23
- ): Promise<void> {
24
- const effectiveBatchSize = Number(options.batchSize) || 1000;
25
- const progress = new ProgressReporter(options);
26
-
27
- let fromFormat = options.from?.toLowerCase();
28
- if (!fromFormat && inputPath !== "-") {
29
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
30
- }
31
- if (!fromFormat) {
32
- fromFormat = "csv";
33
- }
34
-
35
- const toFormat = options.to?.toLowerCase() || (fromFormat === "xlsx" ? "csv" : fromFormat);
36
- const mapping = parseRenameSpecs(specs);
37
-
38
- const inputStream = openReadableStream(inputPath);
39
- const reader = createReader(inputStream, {
40
- format: fromFormat,
41
- sheet: options.sheet,
42
- delimiter: options.delimiter,
43
- batchSize: effectiveBatchSize,
44
- filePath: inputPath,
45
- });
46
-
47
- const writer = createWriter(process.stdout, {
48
- format: toFormat,
49
- delimiter: options.delimiter,
50
- });
51
-
52
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
53
- pipeline.pipe(renameColumns(mapping));
54
- pipeline.onProgress((info) => progress.update(info));
55
-
56
- await pipeline.to(writer);
57
- progress.done();
58
- logMemoryDebug();
59
- }
@@ -1,61 +0,0 @@
1
- import { createPipeline } from "../../core/pipeline.js";
2
- import { createReader, inferFormatFromPath as inferReaderFormat } from "../../readers/index.js";
3
- import { createWriter } from "../../writers/index.js";
4
- import { sampleRows } from "../../transforms/sample.js";
5
- import { openReadableStream } from "../../utils/compression.js";
6
- import { logMemoryDebug } from "../../utils/formatting.js";
7
- import { ProgressReporter } from "../../utils/progress.js";
8
-
9
- export interface SampleCommandOptions {
10
- rows?: string | number;
11
- seed?: string | number;
12
- from?: string;
13
- to?: string;
14
- sheet?: string;
15
- delimiter?: string;
16
- batchSize?: string | number;
17
- quiet?: boolean;
18
- noProgress?: boolean;
19
- }
20
-
21
- export async function sampleCommand(
22
- inputPath = "-",
23
- options: SampleCommandOptions = {}
24
- ): Promise<void> {
25
- const sampleCount = options.rows !== undefined ? Number(options.rows) : 1000;
26
- const seed = options.seed !== undefined ? Number(options.seed) : undefined;
27
- const effectiveBatchSize = Number(options.batchSize) || 1000;
28
- const progress = new ProgressReporter(options);
29
-
30
- let fromFormat = options.from?.toLowerCase();
31
- if (!fromFormat && inputPath !== "-") {
32
- fromFormat = inferReaderFormat(inputPath) ?? undefined;
33
- }
34
- if (!fromFormat) {
35
- fromFormat = "csv";
36
- }
37
-
38
- const toFormat = options.to?.toLowerCase() || (fromFormat === "xlsx" ? "csv" : fromFormat);
39
-
40
- const inputStream = openReadableStream(inputPath);
41
- const reader = createReader(inputStream, {
42
- format: fromFormat,
43
- sheet: options.sheet,
44
- delimiter: options.delimiter,
45
- batchSize: effectiveBatchSize,
46
- filePath: inputPath,
47
- });
48
-
49
- const writer = createWriter(process.stdout, {
50
- format: toFormat,
51
- delimiter: options.delimiter,
52
- });
53
-
54
- const pipeline = createPipeline(reader, { batchSize: effectiveBatchSize });
55
- pipeline.pipe(sampleRows({ rows: sampleCount, seed }));
56
- pipeline.onProgress((info) => progress.update(info));
57
-
58
- await pipeline.to(writer);
59
- progress.done();
60
- logMemoryDebug();
61
- }