edf2csv 0.7.253 → 0.7.255

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.
package/dist/cli.js CHANGED
@@ -97,6 +97,13 @@ Examples
97
97
  edf2csv /data/*.edf --out ./converted --jobs auto
98
98
  edf2csv /data/study --out ./converted --jobs auto
99
99
  `;
100
+ /**
101
+ * The placeholder `--help` writes after each option that takes a value, read off `--help`.
102
+ *
103
+ * Read rather than listed again so the two cannot part company: `--channels <list>` is what
104
+ * the usage block says and what the reference documents, and the refusals below quote it back.
105
+ */
106
+ const VALUE_NAMES = new Map([...USAGE.matchAll(/--([a-z-]+) (<[a-z]+>)/gu)].map((m) => [m[1], m[2]]));
100
107
  /**
101
108
  * A continuation line under an `error: ` or `interrupted (SIGINT): ` head.
102
109
  *
@@ -576,7 +583,7 @@ export async function main(argv) {
576
583
  clause: there is no output to say was still written.
577
584
  */
578
585
  if (strict && warnings > 0) {
579
- process.stderr.write(`\n${wrap(`--strict: ${warnings} warning${warnings === 1 ? '' : 's'} raised, so this run is ` +
586
+ process.stderr.write(`\n${wrap(`--strict: ${counted(warnings, 'warning')} raised, so this run is ` +
580
587
  `reported as a failure. Nothing was written either way, since --info converts nothing.`)}\n`);
581
588
  return EXIT_ERROR;
582
589
  }
@@ -679,8 +686,8 @@ export async function main(argv) {
679
686
  */
680
687
  const started = abandoned.filter((destination) => existsSync(destination));
681
688
  const untouched = abandoned.filter((destination) => !existsSync(destination));
682
- process.stderr.write(`\ninterrupted (${signal}): ${abandoned.length} conversion` +
683
- `${abandoned.length === 1 ? '' : 's'} stopped part way through.\n` +
689
+ process.stderr.write(`\ninterrupted (${signal}): ${counted(abandoned.length, 'conversion')} ` +
690
+ `stopped part way through.\n` +
684
691
  (started.length > 0
685
692
  ? detail(`Incomplete, and should not be used: ${listed(started.map(printable))}`)
686
693
  : '') +
@@ -761,7 +768,7 @@ export async function main(argv) {
761
768
  failures.push(EXIT_ERROR);
762
769
  if (batch && !quiet && !asJson) {
763
770
  const unread = unreadable.length > 0
764
- ? `; ${unreadable.length} path${unreadable.length === 1 ? '' : 's'} could not be read`
771
+ ? `; ${counted(unreadable.length, 'path')} could not be read`
765
772
  : '';
766
773
  const failed = converted < inputs.length ? `; ${inputs.length - converted} failed` : '';
767
774
  process.stderr.write(`\nConverted ${converted} of ${counted(inputs.length, 'recording')}${failed}${unread}.\n`);
@@ -789,7 +796,7 @@ export async function main(argv) {
789
796
  to do about it is the caller's decision, and they still have the files to inspect.
790
797
  */
791
798
  if (strict && warnings > 0) {
792
- process.stderr.write(`\n${wrap(`--strict: ${warnings} warning${warnings === 1 ? '' : 's'} raised, so this run is ` +
799
+ process.stderr.write(`\n${wrap(`--strict: ${counted(warnings, 'warning')} raised, so this run is ` +
793
800
  `reported as a failure. The output was still written.`)}\n`);
794
801
  return EXIT_ERROR;
795
802
  }
@@ -1983,6 +1990,17 @@ function survivesBare(text) {
1983
1990
  function singleQuoted(text) {
1984
1991
  return `'${text.replaceAll("'", "'\\''")}'`;
1985
1992
  }
1993
+ /**
1994
+ * Which spelling of an option the command actually used.
1995
+ *
1996
+ * Node names both — `-c, --channels` — and the reader typed one of them. Quoting the pair back
1997
+ * makes a refusal about a command nobody wrote.
1998
+ */
1999
+ function asTyped(short, long, argv) {
2000
+ if (short === undefined)
2001
+ return long;
2002
+ return argv.some((a) => a === long || a.startsWith(`${long}=`)) ? long : short;
2003
+ }
1986
2004
  /**
1987
2005
  * A `parseArgs` failure, in this tool's words where they are better than Node's.
1988
2006
  *
@@ -2030,6 +2048,37 @@ function usageMessage(error, argv) {
2030
2048
  if (code !== 'ERR_PARSE_ARGS_INVALID_OPTION_VALUE') {
2031
2049
  return asError(raw);
2032
2050
  }
2051
+ /*
2052
+ Node's voice, in the two refusals this file had not taken over.
2053
+
2054
+ `unknownOption` and the ambiguous-value branch below both rewrite their message into this
2055
+ tool's words. Forgetting a value did not, so the commonest slip of the three came back as
2056
+
2057
+ error: Option '-c, --channels <value>' argument missing
2058
+
2059
+ which names both spellings when the reader typed one, ends without the full stop 68 of
2060
+ this tool's 69 diagnostics carry, and quotes a placeholder — `<value>` — that appears
2061
+ nowhere in `--help`, the reference, or any other message here: this option takes a
2062
+ `<list>`, `--start` takes a `<time>`, `--out` a `<dir>`. Nothing in it tells the reader
2063
+ what to write, and it is the one refusal where that is the whole question.
2064
+
2065
+ `--gzip=yes` is the same failure from the other side, and had the same treatment.
2066
+ */
2067
+ const missing = /^Option '(?:(-[A-Za-z]), )?(--[a-z-]+) <value>' argument missing$/u.exec(raw);
2068
+ if (missing) {
2069
+ const long = missing[2];
2070
+ return printableLines(`error: ${asTyped(missing[1], long, argv)} needs a value and was given none.\n` +
2071
+ ` It takes one: ${long} ${VALUE_NAMES.get(long.slice(2)) ?? '<value>'}.`);
2072
+ }
2073
+ const unwanted = /^Option '(?:(-[A-Za-z]), )?(--[a-z-]+)' does not take an argument$/u.exec(raw);
2074
+ if (unwanted) {
2075
+ const long = unwanted[2];
2076
+ const typed = asTyped(unwanted[1], long, argv);
2077
+ const given = argv.find((a) => a.startsWith(`${long}=`))?.slice(long.length + 1);
2078
+ return printableLines(`error: ${typed} is a switch and takes no value` +
2079
+ `${given === undefined ? '' : `, but was given "${given}"`}.\n` +
2080
+ ` Write it on its own: ${typed}`);
2081
+ }
2033
2082
  const ambiguous = /^Option '(-[^']+)' argument is ambiguous/u.exec(raw);
2034
2083
  if (!ambiguous)
2035
2084
  return asError(raw);