@lde/pipeline-console-reporter 0.15.6 → 0.16.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.
@@ -1,16 +1,17 @@
1
1
  import type { Dataset, Distribution } from '@lde/dataset';
2
2
  import type { DistributionAnalysisResult, ProgressReporter, ValidationReport } from '@lde/pipeline';
3
3
  export declare class ConsoleReporter implements ProgressReporter {
4
- private stageSpinner?;
4
+ private activeSpinner?;
5
5
  private stageStartTime;
6
6
  private datasetStartTime;
7
7
  private datasetTotal;
8
8
  private datasetIndex;
9
- private importSpinner?;
10
9
  private importTimer?;
11
10
  private probeLines;
12
11
  /** Print a static succeed/fail line without starting a spinner animation. */
13
12
  private printLine;
13
+ /** Stop any active spinner and start a new one. */
14
+ private startSpinner;
14
15
  pipelineStart(_name: string): void;
15
16
  datasetsSelected(count: number, duration: number): void;
16
17
  datasetStart(dataset: Dataset): void;
@@ -18,11 +19,12 @@ export declare class ConsoleReporter implements ProgressReporter {
18
19
  importStarted(): void;
19
20
  importFailed(_distribution: Distribution, error: string): void;
20
21
  distributionSelected(_dataset: Dataset, distribution: Distribution, importedFrom?: Distribution, importDuration?: number, tripleCount?: number): void;
21
- private clearImportSpinner;
22
+ private clearImportTimer;
22
23
  stageStart(stage: string): void;
23
24
  stageProgress(update: {
24
25
  itemsProcessed: number;
25
26
  quadsGenerated: number;
27
+ memoryUsageBytes: number;
26
28
  }): void;
27
29
  stageComplete(_stage: string, result: {
28
30
  itemsProcessed: number;
@@ -32,10 +34,13 @@ export declare class ConsoleReporter implements ProgressReporter {
32
34
  stageFailed(_stage: string, error: Error): void;
33
35
  stageValidated(_stage: string, report: ValidationReport): void;
34
36
  stageSkipped(_stage: string, reason: string): void;
35
- datasetComplete(_dataset: Dataset): void;
37
+ datasetComplete(_dataset: Dataset, result: {
38
+ memoryUsageBytes: number;
39
+ }): void;
36
40
  datasetSkipped(_dataset: Dataset, reason: string): void;
37
41
  pipelineComplete(result: {
38
42
  duration: number;
43
+ memoryUsageBytes: number;
39
44
  }): void;
40
45
  }
41
46
  //# sourceMappingURL=consoleReporter.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"consoleReporter.d.ts","sourceRoot":"","sources":["../src/consoleReporter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAC;AAC1D,OAAO,KAAK,EACV,0BAA0B,EAC1B,gBAAgB,EAChB,gBAAgB,EACjB,MAAM,eAAe,CAAC;AAUvB,qBAAa,eAAgB,YAAW,gBAAgB;IACtD,OAAO,CAAC,YAAY,CAAC,CAAM;IAC3B,OAAO,CAAC,cAAc,CAAK;IAC3B,OAAO,CAAC,gBAAgB,CAAK;IAC7B,OAAO,CAAC,YAAY,CAAK;IACzB,OAAO,CAAC,YAAY,CAAK;IACzB,OAAO,CAAC,aAAa,CAAC,CAAM;IAC5B,OAAO,CAAC,WAAW,CAAC,CAAiC;IACrD,OAAO,CAAC,UAAU,CAAuC;IAEzD,6EAA6E;IAC7E,OAAO,CAAC,SAAS;IAIjB,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAOlC,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,IAAI;IASvD,YAAY,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI;IAepC,kBAAkB,CAAC,MAAM,EAAE,0BAA0B,GAAG,IAAI;IA0B5D,aAAa,IAAI,IAAI;IAYrB,YAAY,CAAC,aAAa,EAAE,YAAY,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI;IAS9D,oBAAoB,CAClB,QAAQ,EAAE,OAAO,EACjB,YAAY,EAAE,YAAY,EAC1B,YAAY,CAAC,EAAE,YAAY,EAC3B,cAAc,CAAC,EAAE,MAAM,EACvB,WAAW,CAAC,EAAE,MAAM,GACnB,IAAI;IAqCP,OAAO,CAAC,kBAAkB;IAQ1B,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAM/B,aAAa,CAAC,MAAM,EAAE;QACpB,cAAc,EAAE,MAAM,CAAC;QACvB,cAAc,EAAE,MAAM,CAAC;KACxB,GAAG,IAAI;IAWR,aAAa,CACX,MAAM,EAAE,MAAM,EACd,MAAM,EAAE;QACN,cAAc,EAAE,MAAM,CAAC;QACvB,cAAc,EAAE,MAAM,CAAC;QACvB,QAAQ,EAAE,MAAM,CAAC;KAClB,GACA,IAAI;IAUP,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,GAAG,IAAI;IAQ/C,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,gBAAgB,GAAG,IAAI;IAc9D,YAAY,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI;IAQlD,eAAe,CAAC,QAAQ,EAAE,OAAO,GAAG,IAAI;IASxC,cAAc,CAAC,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI;IAIvD,gBAAgB,CAAC,MAAM,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI;CAOrD"}
1
+ {"version":3,"file":"consoleReporter.d.ts","sourceRoot":"","sources":["../src/consoleReporter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAC;AAC1D,OAAO,KAAK,EACV,0BAA0B,EAC1B,gBAAgB,EAChB,gBAAgB,EACjB,MAAM,eAAe,CAAC;AAgBvB,qBAAa,eAAgB,YAAW,gBAAgB;IACtD,OAAO,CAAC,aAAa,CAAC,CAAM;IAC5B,OAAO,CAAC,cAAc,CAAK;IAC3B,OAAO,CAAC,gBAAgB,CAAK;IAC7B,OAAO,CAAC,YAAY,CAAK;IACzB,OAAO,CAAC,YAAY,CAAK;IACzB,OAAO,CAAC,WAAW,CAAC,CAAiC;IACrD,OAAO,CAAC,UAAU,CAAuC;IAEzD,6EAA6E;IAC7E,OAAO,CAAC,SAAS;IAKjB,mDAAmD;IACnD,OAAO,CAAC,YAAY;IAOpB,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAIlC,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,IAAI;IASvD,YAAY,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI;IAgBpC,kBAAkB,CAAC,MAAM,EAAE,0BAA0B,GAAG,IAAI;IA0B5D,aAAa,IAAI,IAAI;IAUrB,YAAY,CAAC,aAAa,EAAE,YAAY,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI;IAY9D,oBAAoB,CAClB,QAAQ,EAAE,OAAO,EACjB,YAAY,EAAE,YAAY,EAC1B,YAAY,CAAC,EAAE,YAAY,EAC3B,cAAc,CAAC,EAAE,MAAM,EACvB,WAAW,CAAC,EAAE,MAAM,GACnB,IAAI;IA0CP,OAAO,CAAC,gBAAgB;IAOxB,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAK/B,aAAa,CAAC,MAAM,EAAE;QACpB,cAAc,EAAE,MAAM,CAAC;QACvB,cAAc,EAAE,MAAM,CAAC;QACvB,gBAAgB,EAAE,MAAM,CAAC;KAC1B,GAAG,IAAI;IAWR,aAAa,CACX,MAAM,EAAE,MAAM,EACd,MAAM,EAAE;QACN,cAAc,EAAE,MAAM,CAAC;QACvB,cAAc,EAAE,MAAM,CAAC;QACvB,QAAQ,EAAE,MAAM,CAAC;KAClB,GACA,IAAI;IAUP,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,KAAK,GAAG,IAAI;IAQ/C,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,gBAAgB,GAAG,IAAI;IAc9D,YAAY,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI;IAQlD,eAAe,CACb,QAAQ,EAAE,OAAO,EACjB,MAAM,EAAE;QAAE,gBAAgB,EAAE,MAAM,CAAA;KAAE,GACnC,IAAI;IASP,cAAc,CAAC,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI;IAIvD,gBAAgB,CAAC,MAAM,EAAE;QACvB,QAAQ,EAAE,MAAM,CAAC;QACjB,gBAAgB,EAAE,MAAM,CAAC;KAC1B,GAAG,IAAI;CAOT"}
@@ -1,38 +1,48 @@
1
1
  import chalk from 'chalk';
2
+ import logSymbols from 'log-symbols';
2
3
  import ora from 'ora';
3
4
  import prettyMilliseconds from 'pretty-ms';
4
5
  const compactNumber = new Intl.NumberFormat('en', {
5
6
  notation: 'compact',
6
7
  maximumFractionDigits: 1,
7
8
  });
9
+ function formatBytes(bytes) {
10
+ const megabytes = bytes / 1024 / 1024;
11
+ return `${megabytes.toFixed(0)} MB`;
12
+ }
8
13
  export class ConsoleReporter {
9
- stageSpinner;
14
+ activeSpinner;
10
15
  stageStartTime = 0;
11
16
  datasetStartTime = 0;
12
17
  datasetTotal = 0;
13
18
  datasetIndex = 0;
14
- importSpinner;
15
19
  importTimer;
16
20
  probeLines = [];
17
21
  /** Print a static succeed/fail line without starting a spinner animation. */
18
22
  printLine(method, text) {
19
- ora({ discardStdin: false })[method](text);
23
+ const symbol = method === 'succeed' ? logSymbols.success : logSymbols.error;
24
+ process.stderr.write(`${symbol} ${text}\n`);
25
+ }
26
+ /** Stop any active spinner and start a new one. */
27
+ startSpinner(text) {
28
+ this.activeSpinner?.stop();
29
+ this.clearImportTimer();
30
+ this.activeSpinner = ora({ discardStdin: false }).start(text);
31
+ return this.activeSpinner;
20
32
  }
21
33
  pipelineStart(_name) {
22
- this.stageSpinner = ora({
23
- discardStdin: false,
24
- text: 'Selecting datasets',
25
- }).start();
34
+ this.startSpinner('Selecting datasets');
26
35
  }
27
36
  datasetsSelected(count, duration) {
28
37
  this.datasetTotal = count;
29
- if (this.stageSpinner) {
30
- this.stageSpinner.text = `Selected datasets: found ${chalk.bold(count)} ${count === 1 ? 'dataset' : 'datasets'} in ${chalk.bold(prettyMilliseconds(duration))}`;
38
+ if (this.activeSpinner) {
39
+ this.activeSpinner.text = `Selected datasets: found ${chalk.bold(count)} ${count === 1 ? 'dataset' : 'datasets'} in ${chalk.bold(prettyMilliseconds(duration))}`;
31
40
  }
32
41
  }
33
42
  datasetStart(dataset) {
34
- this.stageSpinner?.succeed();
35
- this.stageSpinner = undefined;
43
+ this.activeSpinner?.succeed();
44
+ this.activeSpinner = undefined;
45
+ this.clearImportTimer();
36
46
  this.datasetStartTime = Date.now();
37
47
  this.probeLines = [];
38
48
  this.datasetIndex++;
@@ -66,37 +76,47 @@ export class ConsoleReporter {
66
76
  }
67
77
  importStarted() {
68
78
  const importStart = Date.now();
69
- this.importSpinner = ora({ discardStdin: false }).start('Importing\u2026');
79
+ const spinner = this.startSpinner('Importing\u2026');
70
80
  this.importTimer = setInterval(() => {
71
- if (this.importSpinner) {
72
- this.importSpinner.suffixText = prettyMilliseconds(Date.now() - importStart);
81
+ if (spinner.isSpinning) {
82
+ spinner.suffixText = prettyMilliseconds(Date.now() - importStart);
73
83
  }
74
84
  }, 1_000);
75
85
  }
76
86
  importFailed(_distribution, error) {
77
- const spinner = this.importSpinner ?? ora({ discardStdin: false });
78
- if (!this.importSpinner)
79
- spinner.start();
80
- spinner.text = `Import failed: ${error}`;
81
- spinner.suffixText = '';
82
- spinner.fail();
83
- this.clearImportSpinner();
87
+ if (this.activeSpinner) {
88
+ this.activeSpinner.text = `Import failed: ${error}`;
89
+ this.activeSpinner.suffixText = '';
90
+ this.activeSpinner.fail();
91
+ }
92
+ else {
93
+ this.printLine('fail', `Import failed: ${error}`);
94
+ }
95
+ this.clearImportTimer();
96
+ this.activeSpinner = undefined;
84
97
  }
85
98
  distributionSelected(_dataset, distribution, importedFrom, importDuration, tripleCount) {
86
99
  if (importedFrom) {
87
- const spinner = this.importSpinner ?? ora({ discardStdin: false }).start();
88
100
  const count = tripleCount !== undefined
89
101
  ? `${compactNumber.format(tripleCount)} triples, `
90
102
  : '';
91
103
  const duration = importDuration !== undefined
92
104
  ? ` in ${chalk.bold(prettyMilliseconds(importDuration))}`
93
105
  : '';
94
- spinner.text = `Imported ${importedFrom.accessUrl.toString()} (${count}to ${distribution.accessUrl.toString()})${duration}`;
95
- spinner.suffixText = '';
96
- spinner.succeed();
97
- this.clearImportSpinner();
106
+ const text = `Imported ${importedFrom.accessUrl.toString()} (${count}to ${distribution.accessUrl.toString()})${duration}`;
107
+ if (this.activeSpinner) {
108
+ this.activeSpinner.text = text;
109
+ this.activeSpinner.suffixText = '';
110
+ this.activeSpinner.succeed();
111
+ }
112
+ else {
113
+ this.printLine('succeed', text);
114
+ }
115
+ this.clearImportTimer();
116
+ this.activeSpinner = undefined;
98
117
  }
99
118
  else {
119
+ this.clearImportTimer(); // defensive — prevents leaks from a previous dataset
100
120
  const url = distribution.accessUrl.toString();
101
121
  const probe = this.probeLines.find((line) => line.url === url);
102
122
  const text = probe?.text || url;
@@ -116,36 +136,34 @@ export class ConsoleReporter {
116
136
  }
117
137
  }
118
138
  }
119
- clearImportSpinner() {
139
+ clearImportTimer() {
120
140
  if (this.importTimer) {
121
141
  clearInterval(this.importTimer);
122
142
  this.importTimer = undefined;
123
143
  }
124
- this.importSpinner = undefined;
125
144
  }
126
145
  stageStart(stage) {
127
146
  this.stageStartTime = Date.now();
128
- this.stageSpinner = ora({ discardStdin: false }).start();
129
- this.stageSpinner.text = `Stage ${chalk.bold(stage)}`;
147
+ this.startSpinner(`Stage ${chalk.bold(stage)}`);
130
148
  }
131
149
  stageProgress(update) {
132
- if (this.stageSpinner) {
150
+ if (this.activeSpinner) {
133
151
  const elapsed = prettyMilliseconds(Date.now() - this.stageStartTime);
134
- this.stageSpinner.suffixText = `${compactNumber.format(update.itemsProcessed)} items, ${compactNumber.format(update.quadsGenerated)} quads, ${elapsed}`;
152
+ this.activeSpinner.suffixText = `${compactNumber.format(update.itemsProcessed)} items, ${compactNumber.format(update.quadsGenerated)} quads, ${elapsed}, memory: ${formatBytes(update.memoryUsageBytes)}`;
135
153
  }
136
154
  }
137
155
  stageComplete(_stage, result) {
138
- if (this.stageSpinner) {
139
- this.stageSpinner.suffixText = `took ${chalk.bold(prettyMilliseconds(result.duration))}`;
140
- this.stageSpinner.succeed();
141
- this.stageSpinner = undefined;
156
+ if (this.activeSpinner) {
157
+ this.activeSpinner.suffixText = `took ${chalk.bold(prettyMilliseconds(result.duration))}`;
158
+ this.activeSpinner.succeed();
159
+ this.activeSpinner = undefined;
142
160
  }
143
161
  }
144
162
  stageFailed(_stage, error) {
145
- if (this.stageSpinner) {
146
- this.stageSpinner.suffixText = chalk.red(error.message);
147
- this.stageSpinner.fail();
148
- this.stageSpinner = undefined;
163
+ if (this.activeSpinner) {
164
+ this.activeSpinner.suffixText = chalk.red(error.message);
165
+ this.activeSpinner.fail();
166
+ this.activeSpinner = undefined;
149
167
  }
150
168
  }
151
169
  stageValidated(_stage, report) {
@@ -157,19 +175,19 @@ export class ConsoleReporter {
157
175
  }
158
176
  }
159
177
  stageSkipped(_stage, reason) {
160
- if (this.stageSpinner) {
161
- this.stageSpinner.suffixText = `skipped: ${chalk.red(reason)}`;
162
- this.stageSpinner.fail();
163
- this.stageSpinner = undefined;
178
+ if (this.activeSpinner) {
179
+ this.activeSpinner.suffixText = `skipped: ${chalk.red(reason)}`;
180
+ this.activeSpinner.fail();
181
+ this.activeSpinner = undefined;
164
182
  }
165
183
  }
166
- datasetComplete(_dataset) {
167
- this.printLine('succeed', `Completed in ${chalk.bold(prettyMilliseconds(Date.now() - this.datasetStartTime))}`);
184
+ datasetComplete(_dataset, result) {
185
+ this.printLine('succeed', `Completed in ${chalk.bold(prettyMilliseconds(Date.now() - this.datasetStartTime))} ${chalk.dim(`(memory: ${formatBytes(result.memoryUsageBytes)})`)}`);
168
186
  }
169
187
  datasetSkipped(_dataset, reason) {
170
188
  this.printLine('fail', `Skipped: ${chalk.red(reason)}`);
171
189
  }
172
190
  pipelineComplete(result) {
173
- process.stderr.write(`\nPipeline completed in ${chalk.bold(prettyMilliseconds(result.duration))}\n`);
191
+ process.stderr.write(`\nPipeline completed in ${chalk.bold(prettyMilliseconds(result.duration))} ${chalk.dim(`(memory: ${formatBytes(result.memoryUsageBytes)})`)}\n`);
174
192
  }
175
193
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lde/pipeline-console-reporter",
3
- "version": "0.15.6",
3
+ "version": "0.16.0",
4
4
  "description": "Console progress reporter for @lde/pipeline",
5
5
  "repository": {
6
6
  "url": "git+https://github.com/ldelements/lde.git",
@@ -25,12 +25,13 @@
25
25
  ],
26
26
  "dependencies": {
27
27
  "chalk": "^5.4.1",
28
+ "log-symbols": "^7.0.0",
28
29
  "ora": "^9.3.0",
29
30
  "pretty-ms": "^9.3.0",
30
31
  "tslib": "^2.3.0"
31
32
  },
32
33
  "peerDependencies": {
33
34
  "@lde/dataset": "0.7.2",
34
- "@lde/pipeline": "0.24.4"
35
+ "@lde/pipeline": "0.25.0"
35
36
  }
36
37
  }