mdat-plugin-cli-help 1.0.7 → 2.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.
package/dist/index.d.ts CHANGED
@@ -1,13 +1,15 @@
1
- import * as type_fest0 from "type-fest";
1
+ import * as _$mdat from "mdat";
2
+ import { ILogBasic, ILogLayer } from "lognow";
2
3
 
4
+ //#region src/utilities/log.d.ts
5
+ /**
6
+ * Set the logger instance for the module.
7
+ * Export this for library consumers to inject their own logger.
8
+ * @param logger - Accepts either a LogLayer instance or a Console- or Stream-like log target
9
+ */
10
+ declare function setLogger(logger?: ILogBasic | ILogLayer): void;
11
+ //#endregion
3
12
  //#region src/index.d.ts
4
- declare const _default: {
5
- cli: {
6
- content(options?: type_fest0.JsonValue | undefined): Promise<string>;
7
- };
8
- 'cli-help': {
9
- content(options?: type_fest0.JsonValue | undefined): Promise<string>;
10
- };
11
- };
13
+ declare const _default: _$mdat.Config;
12
14
  //#endregion
13
- export { _default as default };
15
+ export { _default as default, setLogger };
package/dist/index.js CHANGED
@@ -1,14 +1,12 @@
1
+ import { defineConfig, getContextMetadata } from "mdat";
1
2
  import { z } from "zod";
2
3
  import { execaCommand } from "execa";
3
- import { log } from "remark-mdat";
4
+ import { createLogger, injectionHelper } from "lognow";
4
5
  import { CstParser, Lexer, createToken } from "chevrotain";
5
6
  import path from "node:path";
6
7
  import which from "which";
7
- import { loadConfig } from "mdat";
8
- import { readPackage } from "read-pkg";
9
8
  import fs from "node:fs/promises";
10
9
  import process from "node:process";
11
-
12
10
  //#region src/utilities/help-object-to-markdown.ts
13
11
  /**
14
12
  * Converts a ProgramInfo object extracted by one of the help parsers into a big
@@ -118,7 +116,23 @@ function findEmptyColumns(rows) {
118
116
  }
119
117
  return emptyColumnsIndexes;
120
118
  }
121
-
119
+ //#endregion
120
+ //#region src/utilities/log.ts
121
+ /**
122
+ * The default logger instance for the library.
123
+ */
124
+ let log = createLogger({
125
+ logToConsole: { showTime: false },
126
+ name: "mdat-plugin-cli-help"
127
+ });
128
+ /**
129
+ * Set the logger instance for the module.
130
+ * Export this for library consumers to inject their own logger.
131
+ * @param logger - Accepts either a LogLayer instance or a Console- or Stream-like log target
132
+ */
133
+ function setLogger(logger) {
134
+ log = injectionHelper(logger);
135
+ }
122
136
  //#endregion
123
137
  //#region src/utilities/parsers/meow.ts
124
138
  const flag$1 = createToken({
@@ -342,7 +356,6 @@ function helpStringToObject$2(helpString) {
342
356
  if (programInfo === void 0) throw new Error("Could not parse help string");
343
357
  return programInfo;
344
358
  }
345
-
346
359
  //#endregion
347
360
  //#region src/utilities/parsers/yargs.ts
348
361
  const flag = createToken({
@@ -658,7 +671,6 @@ function helpStringToObject$1(helpString) {
658
671
  if (programInfo === void 0) throw new Error("Could not parse help string");
659
672
  return programInfo;
660
673
  }
661
-
662
674
  //#endregion
663
675
  //#region src/utilities/parsers/index.ts
664
676
  var parsers_default = {
@@ -682,7 +694,6 @@ function getCommandParts(wholeCommand) {
682
694
  subcommand
683
695
  };
684
696
  }
685
-
686
697
  //#endregion
687
698
  //#region src/utilities/help-string-to-object.ts
688
699
  /**
@@ -695,17 +706,16 @@ function getCommandParts(wholeCommand) {
695
706
  */
696
707
  function helpStringToObject(helpString) {
697
708
  for (const [parserName, helpStringToObjectFunction] of Object.entries(parsers_default)) {
698
- log.info(`Trying to parse help string with ${parserName} parser...`);
709
+ log.debug(`Trying to parse help string with ${parserName} parser...`);
699
710
  try {
700
711
  return helpStringToObjectFunction(helpString);
701
712
  } catch (error) {
702
- if (error instanceof Error) log.info(`Error in "${parserName}" parser: ${String(error)}`);
713
+ if (error instanceof Error) log.error(`Error in "${parserName}" parser: ${String(error)}`);
703
714
  continue;
704
715
  }
705
716
  }
706
717
  log.error("Could not parse help string with any parser");
707
718
  }
708
-
709
719
  //#endregion
710
720
  //#region src/utilities/get-help-markdown.ts
711
721
  /**
@@ -722,7 +732,7 @@ async function getHelpMarkdown(cliCommand, helpFlag = "--help", depth) {
722
732
  }
723
733
  async function renderHelpMarkdownObject(cliCommand, helpFlag, depth, programInfo) {
724
734
  if (depth <= 0) {
725
- log.info(`Max CLI command help depth reached, stopping recursion`);
735
+ log.warn(`Max CLI command help depth reached, stopping recursion`);
726
736
  return "";
727
737
  }
728
738
  let markdown = helpObjectToMarkdown(programInfo, depth);
@@ -758,26 +768,6 @@ async function getHelpString(resolvedCommand) {
758
768
  if (rawHelpString === void 0 || rawHelpString === "") throw new Error(`No result from running CLI help command: "${resolvedCommand}"\n`);
759
769
  return rawHelpString;
760
770
  }
761
-
762
- //#endregion
763
- //#region src/utilities/get-package-json.ts
764
- let packageJson;
765
- /**
766
- * Convenience function for rules
767
- * Load as package json only as needed, memoize
768
- * Rules could call this themselves, but this is more convenient and efficient
769
- * @throws {Error} If no package.json is found
770
- */
771
- async function getPackageJson() {
772
- const { packageFile } = await loadConfig();
773
- if (packageFile === void 0) throw new Error("No packageFile found or set in config");
774
- packageJson ??= await readPackage({ cwd: path.dirname(packageFile) });
775
- return {
776
- packageJson,
777
- packagePath: packageFile
778
- };
779
- }
780
-
781
771
  //#endregion
782
772
  //#region src/utilities/is-executable.ts
783
773
  /**
@@ -798,7 +788,6 @@ async function isExecutable(filePath, strictExtensions = false) {
798
788
  return false;
799
789
  }
800
790
  }
801
-
802
791
  //#endregion
803
792
  //#region src/utilities/infer-command.ts
804
793
  /**
@@ -811,17 +800,23 @@ async function inferCommand(cliCommand) {
811
800
  cliCommand ??= await getFirstBinFromPackage();
812
801
  return ensureExecutable(cliCommand);
813
802
  }
803
+ function firstOf(value) {
804
+ if (value === void 0) return void 0;
805
+ return Array.isArray(value) ? value[0] : value;
806
+ }
814
807
  async function getFirstBinFromPackage() {
815
- const { packageJson, packagePath } = await getPackageJson();
816
- const packageDirectory = path.dirname(packagePath);
817
- if (packageJson.bin) {
818
- const binPath = typeof packageJson.bin === "string" ? path.resolve(packageDirectory, packageJson.bin) : path.resolve(packageDirectory, String(Object.values(packageJson.bin).at(0)));
808
+ const { nodePackageJson } = await getContextMetadata();
809
+ const nodePackage = firstOf(nodePackageJson);
810
+ if (nodePackage?.source !== void 0 && nodePackage.data.bin !== void 0) {
811
+ const packageDirectory = path.dirname(nodePackage.source);
812
+ const packageBin = nodePackage.data.bin;
813
+ const binPath = typeof packageBin === "string" ? path.resolve(packageDirectory, packageBin) : path.resolve(packageDirectory, String(Object.values(packageBin).at(0)));
819
814
  if (looksLikePath(binPath)) {
820
- log.info(`Inferred <!-- cli-help --> command to run from package.json: ${binPath}`);
815
+ log.debug(`Inferred <!-- cli-help --> command to run from package.json: ${binPath}`);
821
816
  return binPath;
822
817
  }
823
818
  }
824
- throw new Error(`Could not infer which command to run for the <!-- cli-help --> rule. Please pass a "cliCommand" option to the expansion comment, e.g. <!-- cli-help {cliCommand: './dist/bin.js'} -->`);
819
+ throw new Error(`Could not infer which command to run for the <!-- cli-help --> rule. Please pass a "cliCommand" option to the expansion comment, e.g. <!-- cli-help({cliCommand: './dist/bin.js'}) -->`);
825
820
  }
826
821
  function looksLikePath(maybePath) {
827
822
  const parsed = path.parse(maybePath);
@@ -834,27 +829,26 @@ async function ensureExecutable(filePath) {
834
829
  throw new Error(`The cli-help rule noticed that "${resolvedPath}" is not executable.`);
835
830
  }
836
831
  async function getCommandPathFromPackage(commandName) {
837
- const { packageJson } = await getPackageJson();
838
- for (const [key, value] of Object.entries(packageJson.bin ?? {})) {
832
+ const { nodePackageJson } = await getContextMetadata();
833
+ const binObject = firstOf(nodePackageJson)?.data.bin;
834
+ if (binObject !== void 0 && typeof binObject !== "string") for (const [key, value] of Object.entries(binObject)) {
839
835
  if (key === commandName) return value;
840
836
  if (path.normalize(value) === path.normalize(commandName)) return value;
841
837
  }
842
838
  }
843
-
844
839
  //#endregion
845
840
  //#region src/index.ts
846
- const cliHelpRule = { async content(options) {
841
+ const cliHelpRule = defineConfig({ cli: { async content(options, _context) {
847
842
  const validOptions = z.object({
848
843
  cliCommand: z.string().optional(),
849
844
  depth: z.number().optional(),
850
845
  helpFlag: z.string().optional()
851
846
  }).optional().parse(options);
852
847
  return getHelpMarkdown(await inferCommand(validOptions?.cliCommand), validOptions?.helpFlag, validOptions?.depth);
853
- } };
854
- var src_default = {
855
- cli: cliHelpRule,
856
- "cli-help": cliHelpRule
857
- };
858
-
848
+ } } });
849
+ var src_default = defineConfig({
850
+ cli: cliHelpRule.cli,
851
+ "cli-help": cliHelpRule.cli
852
+ });
859
853
  //#endregion
860
- export { src_default as default };
854
+ export { src_default as default, setLogger };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mdat-plugin-cli-help",
3
- "version": "1.0.7",
3
+ "version": "2.0.0",
4
4
  "description": "Mdat plugin to generate tabular help documentation for CLI tools in Markdown files.",
5
5
  "keywords": [
6
6
  "markdown",
@@ -21,6 +21,7 @@
21
21
  "email": "eric@ericmika.com",
22
22
  "url": "https://ericmika.com"
23
23
  },
24
+ "sideEffects": false,
24
25
  "type": "module",
25
26
  "exports": {
26
27
  ".": {
@@ -35,30 +36,28 @@
35
36
  ],
36
37
  "dependencies": {
37
38
  "@types/which": "^3.0.4",
38
- "chevrotain": "^11.1.1",
39
+ "chevrotain": "^12.0.0",
39
40
  "execa": "^9.6.1",
40
- "read-pkg": "^10.1.0",
41
- "type-fest": "^5.4.4",
41
+ "lognow": "^0.5.2",
42
+ "type-fest": "^5.5.0",
42
43
  "which": "^6.0.1",
43
- "zod": "^3.25.76"
44
+ "zod": "^4.3.6"
44
45
  },
45
46
  "devDependencies": {
46
- "@kitschpatrol/shared-config": "^6.0.0",
47
- "@types/node": "~20.19.33",
48
- "bumpp": "^10.4.1",
49
- "mdat": "^1.3.5",
47
+ "@kitschpatrol/shared-config": "^6.2.0",
48
+ "@types/node": "~22.17.2",
49
+ "bumpp": "^11.0.1",
50
+ "mdat": "^2.0.0",
50
51
  "meow": "^14.1.0",
51
- "remark-mdat": "^1.2.3",
52
- "tsdown": "^0.20.3",
52
+ "tsdown": "^0.21.7",
53
53
  "typescript": "~5.9.3",
54
- "vitest": "^4.0.18"
54
+ "vitest": "^4.1.2"
55
55
  },
56
56
  "peerDependencies": {
57
- "mdat": "^1.1.0",
58
- "remark-mdat": "^1.1.0"
57
+ "mdat": "^2.0.0"
59
58
  },
60
59
  "engines": {
61
- "node": ">=20.19.0"
60
+ "node": ">=22.17.0"
62
61
  },
63
62
  "devEngines": {
64
63
  "runtime": {
@@ -72,6 +71,6 @@
72
71
  "fix": "ksc fix",
73
72
  "lint": "ksc lint",
74
73
  "release": "bumpp --commit 'Release: %s' && pnpm run build && NPM_AUTH_TOKEN=$(op read 'op://Personal/npm/token') && pnpm publish",
75
- "test": "vitest --no-file-parallelism"
74
+ "test": "vitest run --no-file-parallelism"
76
75
  }
77
76
  }
package/readme.md CHANGED
@@ -1,5 +1,3 @@
1
- <!--+ Warning: Content inside HTML comment blocks was generated by mdat and may be overwritten. +-->
2
-
3
1
  <!-- title -->
4
2
 
5
3
  # mdat-plugin-cli-help
@@ -10,6 +8,7 @@
10
8
 
11
9
  [![NPM Package mdat-plugin-cli-help](https://img.shields.io/npm/v/mdat-plugin-cli-help.svg)](https://npmjs.com/package/mdat-plugin-cli-help)
12
10
  [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
11
+ [![CI](https://github.com/kitschpatrol/mdat-plugin-cli-help/actions/workflows/ci.yml/badge.svg)](https://github.com/kitschpatrol/mdat-plugin-cli-help/actions/workflows/ci.yml)
13
12
 
14
13
  <!-- /badges -->
15
14
 
@@ -46,14 +45,12 @@ pnpm add -D mdat-plugin-cli-help
46
45
  Register the plugin in your mdat config file, e.g. `mdat.config.ts`:
47
46
 
48
47
  ```ts
49
- import type { Config } from 'mdat'
48
+ import { defineConfig } from 'mdat'
50
49
  import cliHelp from 'mdat-plugin-cli-help'
51
50
 
52
- export default {
53
- rules: {
54
- ...cliHelp,
55
- },
56
- } satisfies Config
51
+ export default defineConfig({
52
+ ...cliHelp,
53
+ })
57
54
  ```
58
55
 
59
56
  ## Usage
@@ -61,13 +58,13 @@ export default {
61
58
  Assuming you have an executable with a `--help` flag on your path or in your project's scope:
62
59
 
63
60
  ```markdown
64
- <!-- cli-help { cliCommand: "mdat", depth: 1 } -->
61
+ <!-- cli-help({ cliCommand: "mdat", depth: 1 }) -->
65
62
  ```
66
63
 
67
64
  Then run the `mdat` CLI command on your Markdown file to expand the rule and embed the tabular help output:
68
65
 
69
66
  ````markdown
70
- <!-- cli-help { cliCommand: "mdat", depth: 1 } -->
67
+ <!-- cli-help({ cliCommand: "mdat", depth: 1 }) -->
71
68
 
72
69
  #### Command: `mdat`
73
70
 
@@ -113,7 +110,7 @@ The command is also aliased under the `<!-- cli -->` keyword.
113
110
  This would have equivalent output to the above:
114
111
 
115
112
  ```markdown
116
- <!-- cli { cliCommand: "mdat", depth: 1 } -->
113
+ <!-- cli({ cliCommand: "mdat", depth: 1 }) -->
117
114
  ```
118
115
 
119
116
  If you embed the rule without any arguments, it will look for the binary file listed in the closest `package.json` file and run it with `--help`. This is what you want if you're documenting a package's CLI options in its readme.md file: