@vltpkg/cli-sdk 1.0.0-rc.3 → 1.0.0-rc.30

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 (210) hide show
  1. package/dist/commands/access.d.ts +22 -0
  2. package/dist/commands/access.js +246 -0
  3. package/dist/commands/bugs.d.ts +17 -0
  4. package/dist/commands/bugs.js +163 -0
  5. package/dist/{esm/commands → commands}/build.d.ts +0 -1
  6. package/dist/{esm/commands → commands}/build.js +0 -1
  7. package/dist/{esm/commands → commands}/cache.d.ts +0 -1
  8. package/dist/{esm/commands → commands}/cache.js +0 -1
  9. package/dist/{esm/commands → commands}/ci.d.ts +0 -1
  10. package/dist/{esm/commands → commands}/ci.js +11 -3
  11. package/dist/{esm/commands → commands}/config.d.ts +0 -1
  12. package/dist/{esm/commands → commands}/config.js +6 -1
  13. package/dist/commands/create.d.ts +8 -0
  14. package/dist/commands/create.js +102 -0
  15. package/dist/commands/deprecate.d.ts +13 -0
  16. package/dist/commands/deprecate.js +139 -0
  17. package/dist/commands/dist-tag.d.ts +21 -0
  18. package/dist/commands/dist-tag.js +177 -0
  19. package/dist/{esm/commands → commands}/docs.d.ts +0 -1
  20. package/dist/{esm/commands → commands}/docs.js +2 -3
  21. package/dist/{esm/commands → commands}/exec-cache.d.ts +0 -1
  22. package/dist/{esm/commands → commands}/exec-cache.js +0 -1
  23. package/dist/{esm/commands → commands}/exec-local.d.ts +0 -1
  24. package/dist/{esm/commands → commands}/exec-local.js +23 -1
  25. package/dist/{esm/commands → commands}/exec.d.ts +0 -1
  26. package/dist/{esm/commands → commands}/exec.js +84 -10
  27. package/dist/{esm/commands → commands}/help.d.ts +0 -1
  28. package/dist/{esm/commands → commands}/help.js +5 -1
  29. package/dist/{esm/commands → commands}/init.d.ts +0 -1
  30. package/dist/{esm/commands → commands}/init.js +31 -10
  31. package/dist/{esm/commands → commands}/install/reporter.d.ts +0 -1
  32. package/dist/{esm/commands → commands}/install/reporter.js +0 -1
  33. package/dist/{esm/commands → commands}/install.d.ts +21 -3
  34. package/dist/commands/install.js +140 -0
  35. package/dist/{esm/commands → commands}/list.d.ts +4 -2
  36. package/dist/{esm/commands → commands}/list.js +8 -10
  37. package/dist/{esm/commands → commands}/login.d.ts +0 -1
  38. package/dist/{esm/commands → commands}/login.js +10 -1
  39. package/dist/{esm/commands/token.d.ts → commands/logout.d.ts} +0 -1
  40. package/dist/{esm/commands → commands}/logout.js +10 -1
  41. package/dist/{esm/commands → commands}/pack.d.ts +0 -1
  42. package/dist/{esm/commands → commands}/pack.js +90 -32
  43. package/dist/commands/ping.d.ts +17 -0
  44. package/dist/commands/ping.js +114 -0
  45. package/dist/{esm/commands → commands}/pkg.d.ts +0 -1
  46. package/dist/{esm/commands → commands}/pkg.js +27 -1
  47. package/dist/commands/profile.d.ts +13 -0
  48. package/dist/commands/profile.js +104 -0
  49. package/dist/{esm/commands → commands}/publish.d.ts +1 -2
  50. package/dist/{esm/commands → commands}/publish.js +63 -12
  51. package/dist/{esm/commands → commands}/query.d.ts +4 -2
  52. package/dist/{esm/commands → commands}/query.js +12 -10
  53. package/dist/commands/repo.d.ts +17 -0
  54. package/dist/commands/repo.js +157 -0
  55. package/dist/{esm/commands → commands}/run-exec.d.ts +0 -1
  56. package/dist/commands/run-exec.js +40 -0
  57. package/dist/{esm/commands → commands}/run.d.ts +0 -1
  58. package/dist/{esm/commands → commands}/run.js +27 -1
  59. package/dist/commands/token.d.ts +31 -0
  60. package/dist/commands/token.js +186 -0
  61. package/dist/{esm/commands → commands}/uninstall.d.ts +0 -1
  62. package/dist/{esm/commands → commands}/uninstall.js +16 -3
  63. package/dist/commands/unpublish.d.ts +15 -0
  64. package/dist/commands/unpublish.js +200 -0
  65. package/dist/{esm/commands → commands}/update.d.ts +0 -1
  66. package/dist/{esm/commands → commands}/update.js +6 -1
  67. package/dist/{esm/commands → commands}/version.d.ts +0 -1
  68. package/dist/{esm/commands → commands}/version.js +27 -1
  69. package/dist/commands/view.d.ts +22 -0
  70. package/dist/commands/view.js +334 -0
  71. package/dist/{esm/commands → commands}/whoami.d.ts +0 -1
  72. package/dist/{esm/commands → commands}/whoami.js +10 -1
  73. package/dist/{esm/config → config}/definition.d.ts +39 -19
  74. package/dist/{esm/config → config}/definition.js +74 -39
  75. package/dist/{esm/config → config}/index.d.ts +0 -1
  76. package/dist/{esm/config → config}/index.js +37 -2
  77. package/dist/{esm/config → config}/merge.d.ts +0 -1
  78. package/dist/{esm/config → config}/merge.js +0 -1
  79. package/dist/{esm/config → config}/usage.d.ts +0 -1
  80. package/dist/{esm/config → config}/usage.js +0 -1
  81. package/dist/{esm/custom-help.d.ts → custom-help.d.ts} +0 -1
  82. package/dist/{esm/custom-help.js → custom-help.js} +35 -9
  83. package/dist/{esm/exec-command.d.ts → exec-command.d.ts} +0 -1
  84. package/dist/{esm/exec-command.js → exec-command.js} +14 -8
  85. package/dist/{esm/index.d.ts → index.d.ts} +0 -1
  86. package/dist/{esm/index.js → index.js} +1 -2
  87. package/dist/{esm/load-command.d.ts → load-command.d.ts} +0 -1
  88. package/dist/{esm/load-command.js → load-command.js} +0 -1
  89. package/dist/mermaid-image-view.d.ts +18 -0
  90. package/dist/mermaid-image-view.js +36 -0
  91. package/dist/{esm/output.d.ts → output.d.ts} +2 -2
  92. package/dist/{esm/output.js → output.js} +55 -2
  93. package/dist/{esm/pack-tarball.d.ts → pack-tarball.d.ts} +15 -1
  94. package/dist/{esm/pack-tarball.js → pack-tarball.js} +133 -91
  95. package/dist/{esm/parse-add-remove-args.d.ts → parse-add-remove-args.d.ts} +9 -3
  96. package/dist/{esm/parse-add-remove-args.js → parse-add-remove-args.js} +43 -11
  97. package/dist/{esm/print-err.d.ts → print-err.d.ts} +0 -1
  98. package/dist/{esm/print-err.js → print-err.js} +18 -3
  99. package/dist/query-diff-files.d.ts +17 -0
  100. package/dist/query-diff-files.js +63 -0
  101. package/dist/{esm/query-host-contexts.d.ts → query-host-contexts.d.ts} +0 -1
  102. package/dist/{esm/query-host-contexts.js → query-host-contexts.js} +8 -7
  103. package/dist/{esm/read-password.d.ts → read-password.d.ts} +0 -1
  104. package/dist/{esm/read-password.js → read-password.js} +0 -1
  105. package/dist/read-project-folders.d.ts +17 -0
  106. package/dist/read-project-folders.js +100 -0
  107. package/dist/reload-config.d.ts +2 -0
  108. package/dist/reload-config.js +11 -0
  109. package/dist/render-mermaid.d.ts +22 -0
  110. package/dist/render-mermaid.js +68 -0
  111. package/dist/telemetry.d.ts +58 -0
  112. package/dist/telemetry.js +170 -0
  113. package/dist/{esm/view.d.ts → view.d.ts} +0 -1
  114. package/dist/{esm/view.js → view.js} +1 -2
  115. package/package.json +69 -83
  116. package/dist/esm/commands/build.d.ts.map +0 -1
  117. package/dist/esm/commands/build.js.map +0 -1
  118. package/dist/esm/commands/cache.d.ts.map +0 -1
  119. package/dist/esm/commands/cache.js.map +0 -1
  120. package/dist/esm/commands/ci.d.ts.map +0 -1
  121. package/dist/esm/commands/ci.js.map +0 -1
  122. package/dist/esm/commands/config.d.ts.map +0 -1
  123. package/dist/esm/commands/config.js.map +0 -1
  124. package/dist/esm/commands/docs.d.ts.map +0 -1
  125. package/dist/esm/commands/docs.js.map +0 -1
  126. package/dist/esm/commands/exec-cache.d.ts.map +0 -1
  127. package/dist/esm/commands/exec-cache.js.map +0 -1
  128. package/dist/esm/commands/exec-local.d.ts.map +0 -1
  129. package/dist/esm/commands/exec-local.js.map +0 -1
  130. package/dist/esm/commands/exec.d.ts.map +0 -1
  131. package/dist/esm/commands/exec.js.map +0 -1
  132. package/dist/esm/commands/help.d.ts.map +0 -1
  133. package/dist/esm/commands/help.js.map +0 -1
  134. package/dist/esm/commands/init.d.ts.map +0 -1
  135. package/dist/esm/commands/init.js.map +0 -1
  136. package/dist/esm/commands/install/reporter.d.ts.map +0 -1
  137. package/dist/esm/commands/install/reporter.js.map +0 -1
  138. package/dist/esm/commands/install.d.ts.map +0 -1
  139. package/dist/esm/commands/install.js +0 -45
  140. package/dist/esm/commands/install.js.map +0 -1
  141. package/dist/esm/commands/list.d.ts.map +0 -1
  142. package/dist/esm/commands/list.js.map +0 -1
  143. package/dist/esm/commands/login.d.ts.map +0 -1
  144. package/dist/esm/commands/login.js.map +0 -1
  145. package/dist/esm/commands/logout.d.ts +0 -4
  146. package/dist/esm/commands/logout.d.ts.map +0 -1
  147. package/dist/esm/commands/logout.js.map +0 -1
  148. package/dist/esm/commands/pack.d.ts.map +0 -1
  149. package/dist/esm/commands/pack.js.map +0 -1
  150. package/dist/esm/commands/pkg.d.ts.map +0 -1
  151. package/dist/esm/commands/pkg.js.map +0 -1
  152. package/dist/esm/commands/publish.d.ts.map +0 -1
  153. package/dist/esm/commands/publish.js.map +0 -1
  154. package/dist/esm/commands/query.d.ts.map +0 -1
  155. package/dist/esm/commands/query.js.map +0 -1
  156. package/dist/esm/commands/run-exec.d.ts.map +0 -1
  157. package/dist/esm/commands/run-exec.js +0 -14
  158. package/dist/esm/commands/run-exec.js.map +0 -1
  159. package/dist/esm/commands/run.d.ts.map +0 -1
  160. package/dist/esm/commands/run.js.map +0 -1
  161. package/dist/esm/commands/serve.d.ts +0 -14
  162. package/dist/esm/commands/serve.d.ts.map +0 -1
  163. package/dist/esm/commands/serve.js +0 -103
  164. package/dist/esm/commands/serve.js.map +0 -1
  165. package/dist/esm/commands/token.d.ts.map +0 -1
  166. package/dist/esm/commands/token.js +0 -30
  167. package/dist/esm/commands/token.js.map +0 -1
  168. package/dist/esm/commands/uninstall.d.ts.map +0 -1
  169. package/dist/esm/commands/uninstall.js.map +0 -1
  170. package/dist/esm/commands/update.d.ts.map +0 -1
  171. package/dist/esm/commands/update.js.map +0 -1
  172. package/dist/esm/commands/version.d.ts.map +0 -1
  173. package/dist/esm/commands/version.js.map +0 -1
  174. package/dist/esm/commands/whoami.d.ts.map +0 -1
  175. package/dist/esm/commands/whoami.js.map +0 -1
  176. package/dist/esm/config/definition.d.ts.map +0 -1
  177. package/dist/esm/config/definition.js.map +0 -1
  178. package/dist/esm/config/index.d.ts.map +0 -1
  179. package/dist/esm/config/index.js.map +0 -1
  180. package/dist/esm/config/merge.d.ts.map +0 -1
  181. package/dist/esm/config/merge.js.map +0 -1
  182. package/dist/esm/config/usage.d.ts.map +0 -1
  183. package/dist/esm/config/usage.js.map +0 -1
  184. package/dist/esm/custom-help.d.ts.map +0 -1
  185. package/dist/esm/custom-help.js.map +0 -1
  186. package/dist/esm/exec-command.d.ts.map +0 -1
  187. package/dist/esm/exec-command.js.map +0 -1
  188. package/dist/esm/index.d.ts.map +0 -1
  189. package/dist/esm/index.js.map +0 -1
  190. package/dist/esm/load-command.d.ts.map +0 -1
  191. package/dist/esm/load-command.js.map +0 -1
  192. package/dist/esm/output.d.ts.map +0 -1
  193. package/dist/esm/output.js.map +0 -1
  194. package/dist/esm/pack-tarball.d.ts.map +0 -1
  195. package/dist/esm/pack-tarball.js.map +0 -1
  196. package/dist/esm/package.json +0 -3
  197. package/dist/esm/parse-add-remove-args.d.ts.map +0 -1
  198. package/dist/esm/parse-add-remove-args.js.map +0 -1
  199. package/dist/esm/print-err.d.ts.map +0 -1
  200. package/dist/esm/print-err.js.map +0 -1
  201. package/dist/esm/query-host-contexts.d.ts.map +0 -1
  202. package/dist/esm/query-host-contexts.js.map +0 -1
  203. package/dist/esm/read-password.d.ts.map +0 -1
  204. package/dist/esm/read-password.js.map +0 -1
  205. package/dist/esm/start-gui.d.ts +0 -10
  206. package/dist/esm/start-gui.d.ts.map +0 -1
  207. package/dist/esm/start-gui.js +0 -60
  208. package/dist/esm/start-gui.js.map +0 -1
  209. package/dist/esm/view.d.ts.map +0 -1
  210. package/dist/esm/view.js.map +0 -1
@@ -1,6 +1,7 @@
1
1
  import { homedir } from 'node:os';
2
2
  import { parse, posix } from 'node:path';
3
- import { getProjectData, readProjectFolders, reloadConfig, } from '@vltpkg/server';
3
+ import { readProjectFolders } from "./read-project-folders.js";
4
+ import { reloadConfig } from "./reload-config.js";
4
5
  import { actual, createVirtualRoot } from '@vltpkg/graph';
5
6
  import { SecurityArchive } from '@vltpkg/security-archive';
6
7
  import { error } from '@vltpkg/error-cause';
@@ -13,6 +14,11 @@ try {
13
14
  }
14
15
  catch { }
15
16
  const home = foundHome ?? posix.dirname(posix.format(parse(process.cwd())));
17
+ const isVltInstalled = (folder) => !!folder.resolve('node_modules/.vlt').lstatSync()?.isDirectory() ||
18
+ !!folder
19
+ .resolve('node_modules/.vlt-lock.json')
20
+ .lstatSync()
21
+ ?.isFile();
16
22
  /**
17
23
  * Generates possible project keys for a given folder.
18
24
  */
@@ -89,12 +95,8 @@ export const createHostContextsMap = async (conf) => {
89
95
  for (const folder of projectFolders) {
90
96
  try {
91
97
  const config = await reloadConfig(folder.fullpath());
92
- const projectInfo = getProjectData({
93
- packageJson: config.options.packageJson,
94
- scurry: config.options.scurry,
95
- }, folder);
96
98
  // only include projects that are vlt-installed
97
- if (!projectInfo.vltInstalled) {
99
+ if (!isVltInstalled(folder)) {
98
100
  continue;
99
101
  }
100
102
  // load each individual graph
@@ -132,4 +134,3 @@ export const createHostContextsMap = async (conf) => {
132
134
  });
133
135
  return hostContexts;
134
136
  };
135
- //# sourceMappingURL=query-host-contexts.js.map
@@ -5,4 +5,3 @@ export type Streams = {
5
5
  stdout: NodeJS.WritableStream;
6
6
  };
7
7
  export declare const readPassword: (prompt: string, { stdin, stdout }?: Streams) => Promise<string>;
8
- //# sourceMappingURL=read-password.d.ts.map
@@ -30,4 +30,3 @@ export const readPassword = async (prompt, { stdin, stdout } = process) => {
30
30
  });
31
31
  return input;
32
32
  };
33
- //# sourceMappingURL=read-password.js.map
@@ -0,0 +1,17 @@
1
+ import type { PathBase, PathScurry } from 'path-scurry';
2
+ type ProjectFolderOptions = {
3
+ path?: string;
4
+ scurry: PathScurry;
5
+ userDefinedProjectPaths: string[];
6
+ };
7
+ /**
8
+ * Retrieves folders from a given directory, if that directory is
9
+ * recognized to be the current cli project root folder then we
10
+ * proceed to read its siblings.
11
+ *
12
+ * Traverses nested directory recursively until project folders can
13
+ * be find, always stopping at the first level where a package.json
14
+ * is present.
15
+ */
16
+ export declare const readProjectFolders: ({ path, scurry, userDefinedProjectPaths, }: ProjectFolderOptions, maxDepth?: number) => Promise<PathBase[]>;
17
+ export {};
@@ -0,0 +1,100 @@
1
+ import { availableParallelism, homedir } from 'node:os';
2
+ import { dirname } from 'node:path';
3
+ import { callLimit } from 'promise-call-limit';
4
+ const limit = Math.max(availableParallelism() - 1, 1) * 8;
5
+ let home;
6
+ try {
7
+ home = homedir();
8
+ }
9
+ catch {
10
+ home = dirname(process.cwd());
11
+ }
12
+ const ignoredHomedirFolderNames = [
13
+ 'downloads',
14
+ 'movies',
15
+ 'music',
16
+ 'pictures',
17
+ 'private',
18
+ 'library',
19
+ 'dropbox',
20
+ ].concat(process.platform === 'darwin' ?
21
+ [
22
+ 'public',
23
+ 'private',
24
+ 'applications',
25
+ 'applications (parallels)',
26
+ 'sites',
27
+ 'sync',
28
+ ]
29
+ : process.platform === 'win32' ?
30
+ [
31
+ 'appdata',
32
+ 'application data',
33
+ 'favorites',
34
+ 'links',
35
+ 'videos',
36
+ 'contacts',
37
+ 'searches',
38
+ ]
39
+ : ['videos', 'public']);
40
+ /**
41
+ * Retrieves folders from a given directory, if that directory is
42
+ * recognized to be the current cli project root folder then we
43
+ * proceed to read its siblings.
44
+ *
45
+ * Traverses nested directory recursively until project folders can
46
+ * be find, always stopping at the first level where a package.json
47
+ * is present.
48
+ */
49
+ export const readProjectFolders = async ({ path = home, scurry, userDefinedProjectPaths, }, maxDepth = 7) => {
50
+ const result = [];
51
+ const homeEntry = scurry.cwd.resolve(home);
52
+ const paths = userDefinedProjectPaths.length ? userDefinedProjectPaths : [path];
53
+ const step = (entry, depth) => async () => {
54
+ try {
55
+ for (const child of await entry.readdir()) {
56
+ if (await collectResult(child, result, scurry, entry === homeEntry, depth, maxDepth)) {
57
+ traverse.push(step(child, depth + 1));
58
+ }
59
+ }
60
+ /* c8 ignore next 4 */
61
+ }
62
+ catch {
63
+ // Ignore directories that can't be read.
64
+ // This commonly happens in restricted environments.
65
+ }
66
+ };
67
+ let traverse = (await Promise.all(paths.map(path => scurry.lstat(path))))
68
+ .filter(p => !!p)
69
+ .map(p => step(p, 0));
70
+ // have to do it in phases this way because pushing into the queue
71
+ // during the promise-call-limit confuses its tracking.
72
+ let t;
73
+ do {
74
+ t = traverse;
75
+ traverse = [];
76
+ await callLimit(t, { limit });
77
+ } while (traverse.length);
78
+ return result;
79
+ };
80
+ const collectResult = async (entry, result, scurry, fromHome, depth, maxDepth) => {
81
+ if (!entry.isDirectory() ||
82
+ entry.isSymbolicLink() ||
83
+ entry.name === 'node_modules' ||
84
+ (fromHome &&
85
+ ignoredHomedirFolderNames.includes(entry.name.toLowerCase())) ||
86
+ entry.name.startsWith('.') ||
87
+ depth > maxDepth) {
88
+ return false;
89
+ }
90
+ const resolved = entry.fullpath();
91
+ const statPackageJson = await scurry
92
+ .lstat(`${resolved}/package.json`)
93
+ .catch(() => { });
94
+ const hasValidPackageJson = statPackageJson &&
95
+ statPackageJson.isFile() &&
96
+ !statPackageJson.isSymbolicLink();
97
+ if (hasValidPackageJson)
98
+ result.push(entry);
99
+ return !hasValidPackageJson;
100
+ };
@@ -0,0 +1,2 @@
1
+ import type { ParsedConfig } from './config/index.ts';
2
+ export declare const reloadConfig: (folder: string) => Promise<ParsedConfig>;
@@ -0,0 +1,11 @@
1
+ export const reloadConfig = async (folder) => {
2
+ try {
3
+ const { unload } = (await import('@vltpkg/vlt-json'));
4
+ unload('user');
5
+ unload('project');
6
+ /* c8 ignore next */
7
+ }
8
+ catch { }
9
+ const { Config } = await import("./config/index.js");
10
+ return Config.load(folder, process.argv, true);
11
+ };
@@ -0,0 +1,22 @@
1
+ export type OutputFormat = 'svg' | 'png';
2
+ /**
3
+ * Renders mermaid diagram text to an SVG string using
4
+ * the `beautiful-mermaid` library. No external process
5
+ * is spawned — everything runs in-process.
6
+ * @returns {string} The SVG markup as a string.
7
+ */
8
+ export declare const renderMermaidSvg: (mermaidText: string) => string;
9
+ /**
10
+ * Renders mermaid diagram text to an SVG file.
11
+ * Uses `beautiful-mermaid` in-process, then writes
12
+ * the result to a temp directory.
13
+ * @returns {Promise<string>} The file path of the generated SVG.
14
+ */
15
+ export declare const renderMermaidToFile: (mermaidText: string) => Promise<string>;
16
+ /**
17
+ * Renders mermaid diagram text to a PNG file.
18
+ * Uses `beautiful-mermaid` for SVG, then `@resvg/resvg-wasm`
19
+ * to convert SVG to PNG. Writes to a temp directory.
20
+ * @returns {Promise<string>} The file path of the generated PNG.
21
+ */
22
+ export declare const renderMermaidToPng: (mermaidText: string) => Promise<string>;
@@ -0,0 +1,68 @@
1
+ import { writeFile, mkdtemp } from 'node:fs/promises';
2
+ import { join } from 'node:path';
3
+ import { tmpdir } from 'node:os';
4
+ import { error } from '@vltpkg/error-cause';
5
+ import { renderMermaidSVG } from 'beautiful-mermaid';
6
+ /**
7
+ * Replace `#64;` with `@` for display rendering.
8
+ * Mermaid text uses `#64;` to avoid issues with `@` in
9
+ * GitHub/markdown parsers, but SVG/PNG should show `@`.
10
+ */
11
+ const decodeForDisplay = (mermaidText) => mermaidText.replace(/#64;/g, '@');
12
+ /**
13
+ * Renders mermaid diagram text to an SVG string using
14
+ * the `beautiful-mermaid` library. No external process
15
+ * is spawned — everything runs in-process.
16
+ * @returns {string} The SVG markup as a string.
17
+ */
18
+ export const renderMermaidSvg = (mermaidText) => {
19
+ try {
20
+ return renderMermaidSVG(decodeForDisplay(mermaidText), {
21
+ bg: '#FFFFFF',
22
+ fg: '#27272A',
23
+ padding: 40,
24
+ });
25
+ }
26
+ catch (cause) {
27
+ throw error('Error rendering SVG', { cause });
28
+ }
29
+ };
30
+ /**
31
+ * Renders mermaid diagram text to an SVG file.
32
+ * Uses `beautiful-mermaid` in-process, then writes
33
+ * the result to a temp directory.
34
+ * @returns {Promise<string>} The file path of the generated SVG.
35
+ */
36
+ export const renderMermaidToFile = async (mermaidText) => {
37
+ const svg = renderMermaidSvg(mermaidText);
38
+ const dir = await mkdtemp(join(tmpdir(), 'vlt-mermaid-'));
39
+ const outputFile = join(dir, 'graph.svg');
40
+ await writeFile(outputFile, svg);
41
+ return outputFile;
42
+ };
43
+ /**
44
+ * Renders mermaid diagram text to a PNG file.
45
+ * Uses `beautiful-mermaid` for SVG, then `@resvg/resvg-wasm`
46
+ * to convert SVG to PNG. Writes to a temp directory.
47
+ * @returns {Promise<string>} The file path of the generated PNG.
48
+ */
49
+ export const renderMermaidToPng = async (mermaidText) => {
50
+ const svg = renderMermaidSvg(mermaidText);
51
+ const { Resvg, initWasm } = await import('@resvg/resvg-wasm');
52
+ const { readFile: rf } = await import('node:fs/promises');
53
+ const { createRequire: cr } = await import('node:module');
54
+ const wasmPath = cr(import.meta.url).resolve('@resvg/resvg-wasm/index_bg.wasm');
55
+ try {
56
+ await initWasm(await rf(wasmPath));
57
+ }
58
+ catch {
59
+ // WASM may already be initialized — ignore
60
+ }
61
+ const resvg = new Resvg(svg);
62
+ const pngData = resvg.render();
63
+ const pngBuffer = pngData.asPng();
64
+ const dir = await mkdtemp(join(tmpdir(), 'vlt-mermaid-'));
65
+ const outputFile = join(dir, 'graph.png');
66
+ await writeFile(outputFile, pngBuffer);
67
+ return outputFile;
68
+ };
@@ -0,0 +1,58 @@
1
+ /**
2
+ * Anonymized telemetry for the vlt CLI.
3
+ *
4
+ * - Sends anonymous, non-PII events to PostHog.
5
+ * - Generates a random UUID on first run, stored in XDG data dir.
6
+ * - Respects opt-out via `DO_NOT_TRACK=1`, `VLT_TELEMETRY=0`,
7
+ * or the `--telemetry=false` config flag.
8
+ * - Flush is awaited with a timeout cap so it never blocks CLI exit for long.
9
+ * - Fails silently on any network or runtime error.
10
+ * @module
11
+ */
12
+ /**
13
+ * Check whether telemetry is disabled via environment variables.
14
+ *
15
+ * - `DO_NOT_TRACK=1` — https://consoledonottrack.com/
16
+ * - `VLT_TELEMETRY=0`
17
+ */
18
+ export declare const isOptedOut: () => boolean;
19
+ export interface CommandEvent {
20
+ command: string;
21
+ duration_ms: number;
22
+ success: boolean;
23
+ node_version: string;
24
+ vlt_version: string;
25
+ os: string;
26
+ arch: string;
27
+ ci: boolean;
28
+ }
29
+ export interface InstallEvent {
30
+ dependency_count: number;
31
+ duration_ms: number;
32
+ }
33
+ export interface ErrorEvent {
34
+ command: string;
35
+ error_code?: string;
36
+ }
37
+ /**
38
+ * Capture a `cli_command` event.
39
+ */
40
+ export declare const trackCommand: (ev: CommandEvent, telemetryFlag?: boolean) => void;
41
+ /**
42
+ * Capture a `cli_install` event.
43
+ */
44
+ export declare const trackInstall: (ev: InstallEvent, telemetryFlag?: boolean) => void;
45
+ /**
46
+ * Capture a `cli_error` event.
47
+ */
48
+ export declare const trackError: (ev: ErrorEvent, telemetryFlag?: boolean) => void;
49
+ /**
50
+ * Flush pending events. Returns a promise that resolves once flushing
51
+ * completes **or** when `SHUTDOWN_TIMEOUT_MS` elapses — whichever
52
+ * comes first. Never rejects.
53
+ *
54
+ * The safety-net timer is unreffed so it cannot keep the process alive
55
+ * on its own — if the caller does not `await` this, Node will still
56
+ * exit promptly once all other handles are drained.
57
+ */
58
+ export declare const flush: () => Promise<void>;
@@ -0,0 +1,170 @@
1
+ /**
2
+ * Anonymized telemetry for the vlt CLI.
3
+ *
4
+ * - Sends anonymous, non-PII events to PostHog.
5
+ * - Generates a random UUID on first run, stored in XDG data dir.
6
+ * - Respects opt-out via `DO_NOT_TRACK=1`, `VLT_TELEMETRY=0`,
7
+ * or the `--telemetry=false` config flag.
8
+ * - Flush is awaited with a timeout cap so it never blocks CLI exit for long.
9
+ * - Fails silently on any network or runtime error.
10
+ * @module
11
+ */
12
+ import { randomUUID } from 'node:crypto';
13
+ import { mkdirSync, readFileSync, writeFileSync } from 'node:fs';
14
+ import { createRequire } from 'node:module';
15
+ import { XDG } from '@vltpkg/xdg';
16
+ const POSTHOG_API_KEY = 'phc_k9xCAgC6sPIBLb5UhjhnGWpt1mos0hLV4mmEhZTGPpO';
17
+ const POSTHOG_HOST = 'https://us.i.posthog.com';
18
+ /** Timeout (ms) we wait for PostHog to flush before giving up. */
19
+ const SHUTDOWN_TIMEOUT_MS = 2_000;
20
+ const xdg = new XDG('vlt');
21
+ /**
22
+ * Check whether telemetry is disabled via environment variables.
23
+ *
24
+ * - `DO_NOT_TRACK=1` — https://consoledonottrack.com/
25
+ * - `VLT_TELEMETRY=0`
26
+ */
27
+ export const isOptedOut = () => process.env.DO_NOT_TRACK === '1' ||
28
+ process.env.VLT_TELEMETRY === '0';
29
+ /**
30
+ * Return (or create) a stable anonymous distinct ID.
31
+ * Stored at `<XDG_DATA_HOME>/vlt/telemetry-id`.
32
+ */
33
+ const getAnonymousId = () => {
34
+ const dir = xdg.data();
35
+ const file = xdg.data('telemetry-id');
36
+ try {
37
+ const existing = readFileSync(file, 'utf8').trim();
38
+ if (existing)
39
+ return existing;
40
+ }
41
+ catch {
42
+ // file doesn't exist yet — create it below
43
+ }
44
+ const id = randomUUID();
45
+ try {
46
+ mkdirSync(dir, { recursive: true });
47
+ writeFileSync(file, id + '\n');
48
+ }
49
+ catch {
50
+ // best-effort — if we can't persist, just use a transient id
51
+ }
52
+ return id;
53
+ };
54
+ // ---------------------------------------------------------------------------
55
+ // PostHog client — lazily initialised
56
+ // ---------------------------------------------------------------------------
57
+ let _posthog;
58
+ let _initFailed = false;
59
+ const getClient = () => {
60
+ if (_posthog)
61
+ return _posthog;
62
+ if (_initFailed)
63
+ return undefined;
64
+ try {
65
+ // Dynamic import would be async; posthog-node also ships a
66
+ // synchronous constructor, so we use createRequire to keep
67
+ // the hot-path synchronous in this ESM package.
68
+ const req = createRequire(import.meta.url);
69
+ const { PostHog } = req('posthog-node');
70
+ _posthog = new PostHog(POSTHOG_API_KEY, {
71
+ host: POSTHOG_HOST,
72
+ // Buffer up to 20 events and flush every 10 s — but we always
73
+ // call shutdown at the end so this is just a safety net.
74
+ flushAt: 20,
75
+ flushInterval: 10_000,
76
+ });
77
+ return _posthog;
78
+ /* c8 ignore next 4 */
79
+ }
80
+ catch {
81
+ _initFailed = true;
82
+ return undefined;
83
+ }
84
+ };
85
+ /**
86
+ * Capture a `cli_command` event.
87
+ */
88
+ export const trackCommand = (ev, telemetryFlag) => {
89
+ if (telemetryFlag === false || isOptedOut())
90
+ return;
91
+ const ph = getClient();
92
+ if (!ph)
93
+ return;
94
+ try {
95
+ ph.capture({
96
+ distinctId: getAnonymousId(),
97
+ event: 'cli_command',
98
+ properties: { ...ev },
99
+ });
100
+ }
101
+ catch {
102
+ // fail silently
103
+ }
104
+ };
105
+ /**
106
+ * Capture a `cli_install` event.
107
+ */
108
+ export const trackInstall = (ev, telemetryFlag) => {
109
+ if (telemetryFlag === false || isOptedOut())
110
+ return;
111
+ const ph = getClient();
112
+ if (!ph)
113
+ return;
114
+ try {
115
+ ph.capture({
116
+ distinctId: getAnonymousId(),
117
+ event: 'cli_install',
118
+ properties: { ...ev },
119
+ });
120
+ }
121
+ catch {
122
+ // fail silently
123
+ }
124
+ };
125
+ /**
126
+ * Capture a `cli_error` event.
127
+ */
128
+ export const trackError = (ev, telemetryFlag) => {
129
+ if (telemetryFlag === false || isOptedOut())
130
+ return;
131
+ const ph = getClient();
132
+ if (!ph)
133
+ return;
134
+ try {
135
+ ph.capture({
136
+ distinctId: getAnonymousId(),
137
+ event: 'cli_error',
138
+ properties: { ...ev },
139
+ });
140
+ }
141
+ catch {
142
+ // fail silently
143
+ }
144
+ };
145
+ /**
146
+ * Flush pending events. Returns a promise that resolves once flushing
147
+ * completes **or** when `SHUTDOWN_TIMEOUT_MS` elapses — whichever
148
+ * comes first. Never rejects.
149
+ *
150
+ * The safety-net timer is unreffed so it cannot keep the process alive
151
+ * on its own — if the caller does not `await` this, Node will still
152
+ * exit promptly once all other handles are drained.
153
+ */
154
+ export const flush = () => {
155
+ const ph = _posthog;
156
+ if (!ph)
157
+ return Promise.resolve();
158
+ // Clear the reference so no further events are captured and
159
+ // PostHog's internal timers can be garbage-collected.
160
+ _posthog = undefined;
161
+ return Promise.race([
162
+ ph.shutdown().catch(() => { }),
163
+ new Promise(r => {
164
+ const t = setTimeout(r, SHUTDOWN_TIMEOUT_MS);
165
+ // Unref so this timer alone won't keep the process alive.
166
+ if (typeof t === 'object' && 'unref' in t)
167
+ t.unref();
168
+ }),
169
+ ]);
170
+ };
@@ -27,4 +27,3 @@ export type ViewFn<T = unknown> = (result: T, options: ViewOptions, conf: Loaded
27
27
  export type View<T = unknown> = ViewFn<T> | typeof ViewClass<T>;
28
28
  export declare const isViewClass: <T = unknown>(view: View<T>) => view is typeof ViewClass<T>;
29
29
  export type Views<T = unknown> = View<T> | Record<string, View<T>>;
30
- //# sourceMappingURL=view.d.ts.map
@@ -17,7 +17,7 @@ export class ViewClass {
17
17
  this.config = config;
18
18
  }
19
19
  // TODO: maybe have start() return a flag to say "i got this, do not
20
- // run the command", for example to have the gui just open a web browser
20
+ // run the command", for example to just open a web browser
21
21
  // to the page relevant to a given thing, rather than computing it twice
22
22
  start() { }
23
23
  async done(_result, _opts) {
@@ -28,4 +28,3 @@ export class ViewClass {
28
28
  export const isViewClass = (view) => typeof view === 'function' &&
29
29
  'prototype' in view &&
30
30
  view.prototype instanceof ViewClass;
31
- //# sourceMappingURL=view.js.map