@socketsecurity/cli 1.1.18 → 1.1.20

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 (150) hide show
  1. package/CHANGELOG.md +9 -0
  2. package/bin/npm-cli.js +2 -2
  3. package/bin/npx-cli.js +2 -2
  4. package/bin/pnpm-cli.js +2 -2
  5. package/bin/yarn-cli.js +2 -2
  6. package/dist/cli.js +285 -117
  7. package/dist/cli.js.map +1 -1
  8. package/dist/constants.js +8 -3
  9. package/dist/constants.js.map +1 -1
  10. package/dist/flags.js +3 -2
  11. package/dist/flags.js.map +1 -1
  12. package/dist/npm-cli.js +3 -4
  13. package/dist/npm-cli.js.map +1 -1
  14. package/dist/npx-cli.js +3 -3
  15. package/dist/npx-cli.js.map +1 -1
  16. package/dist/pnpm-cli.js +3 -3
  17. package/dist/pnpm-cli.js.map +1 -1
  18. package/dist/shadow-npm-bin.js +3 -106
  19. package/dist/shadow-npm-bin.js.map +1 -1
  20. package/dist/shadow-npm-bin2.js +125 -0
  21. package/dist/shadow-npm-bin2.js.map +1 -0
  22. package/dist/shadow-npx-bin.js +12 -0
  23. package/dist/shadow-npx-bin.js.map +1 -0
  24. package/dist/shadow-pnpm-bin.js +3 -228
  25. package/dist/shadow-pnpm-bin.js.map +1 -1
  26. package/dist/shadow-pnpm-bin2.js +323 -0
  27. package/dist/shadow-pnpm-bin2.js.map +1 -0
  28. package/dist/shadow-yarn-bin.js +62 -150
  29. package/dist/shadow-yarn-bin.js.map +1 -1
  30. package/dist/tsconfig.dts.tsbuildinfo +1 -1
  31. package/dist/types/commands/analytics/cmd-analytics.d.mts.map +1 -1
  32. package/dist/types/commands/analytics/output-analytics.d.mts.map +1 -1
  33. package/dist/types/commands/audit-log/cmd-audit-log.d.mts.map +1 -1
  34. package/dist/types/commands/audit-log/output-audit-log.d.mts.map +1 -1
  35. package/dist/types/commands/ci/handle-ci.d.mts.map +1 -1
  36. package/dist/types/commands/config/cmd-config-auto.d.mts.map +1 -1
  37. package/dist/types/commands/config/cmd-config-get.d.mts.map +1 -1
  38. package/dist/types/commands/config/cmd-config-list.d.mts.map +1 -1
  39. package/dist/types/commands/config/cmd-config-set.d.mts.map +1 -1
  40. package/dist/types/commands/config/cmd-config-unset.d.mts.map +1 -1
  41. package/dist/types/commands/config/handle-config-set.d.mts.map +1 -1
  42. package/dist/types/commands/fix/cmd-fix.d.mts.map +1 -1
  43. package/dist/types/commands/fix/coana-fix.d.mts.map +1 -1
  44. package/dist/types/commands/fix/handle-fix.d.mts.map +1 -1
  45. package/dist/types/commands/fix/pull-request.d.mts.map +1 -1
  46. package/dist/types/commands/login/attempt-login.d.mts.map +1 -1
  47. package/dist/types/commands/manifest/cmd-manifest-conda.d.mts.map +1 -1
  48. package/dist/types/commands/npm/cmd-npm.d.mts.map +1 -1
  49. package/dist/types/commands/optimize/handle-optimize.d.mts.map +1 -1
  50. package/dist/types/commands/optimize/ls-by-agent.d.mts.map +1 -1
  51. package/dist/types/commands/organization/cmd-organization-dependencies.d.mts.map +1 -1
  52. package/dist/types/commands/organization/cmd-organization-list.d.mts.map +1 -1
  53. package/dist/types/commands/organization/handle-dependencies.d.mts.map +1 -1
  54. package/dist/types/commands/organization/handle-organization-list.d.mts.map +1 -1
  55. package/dist/types/commands/package/handle-purl-deep-score.d.mts.map +1 -1
  56. package/dist/types/commands/package/handle-purls-shallow-score.d.mts.map +1 -1
  57. package/dist/types/commands/pnpm/cmd-pnpm.d.mts.map +1 -1
  58. package/dist/types/commands/raw-npm/run-raw-npm.d.mts.map +1 -1
  59. package/dist/types/commands/raw-npx/run-raw-npx.d.mts.map +1 -1
  60. package/dist/types/commands/repository/cmd-repository-create.d.mts.map +1 -1
  61. package/dist/types/commands/repository/cmd-repository-del.d.mts.map +1 -1
  62. package/dist/types/commands/repository/cmd-repository-list.d.mts.map +1 -1
  63. package/dist/types/commands/repository/cmd-repository-update.d.mts.map +1 -1
  64. package/dist/types/commands/repository/cmd-repository-view.d.mts.map +1 -1
  65. package/dist/types/commands/repository/handle-create-repo.d.mts.map +1 -1
  66. package/dist/types/commands/scan/cmd-scan-create.d.mts.map +1 -1
  67. package/dist/types/commands/scan/cmd-scan-diff.d.mts.map +1 -1
  68. package/dist/types/commands/scan/cmd-scan-list.d.mts.map +1 -1
  69. package/dist/types/commands/scan/create-scan-from-github.d.mts.map +1 -1
  70. package/dist/types/commands/scan/fetch-report-data.d.mts.map +1 -1
  71. package/dist/types/commands/scan/handle-create-new-scan.d.mts.map +1 -1
  72. package/dist/types/commands/scan/output-diff-scan.d.mts.map +1 -1
  73. package/dist/types/commands/scan/output-scan-view.d.mts.map +1 -1
  74. package/dist/types/commands/threat-feed/cmd-threat-feed.d.mts.map +1 -1
  75. package/dist/types/commands/wrapper/postinstall-wrapper.d.mts.map +1 -1
  76. package/dist/types/commands/yarn/cmd-yarn.d.mts.map +1 -1
  77. package/dist/types/constants.d.mts +1 -0
  78. package/dist/types/constants.d.mts.map +1 -1
  79. package/dist/types/flags.d.mts.map +1 -1
  80. package/dist/types/shadow/common.d.mts +31 -0
  81. package/dist/types/shadow/common.d.mts.map +1 -0
  82. package/dist/types/shadow/npm/bin.d.mts +4 -10
  83. package/dist/types/shadow/npm/bin.d.mts.map +1 -1
  84. package/dist/types/shadow/npm-base.d.mts +11 -0
  85. package/dist/types/shadow/npm-base.d.mts.map +1 -0
  86. package/dist/types/shadow/npx/bin.d.mts +5 -0
  87. package/dist/types/shadow/npx/bin.d.mts.map +1 -0
  88. package/dist/types/shadow/pnpm/bin.d.mts +1 -1
  89. package/dist/types/shadow/pnpm/bin.d.mts.map +1 -1
  90. package/dist/types/shadow/stdio-ipc.d.mts +7 -0
  91. package/dist/types/shadow/stdio-ipc.d.mts.map +1 -0
  92. package/dist/types/shadow/yarn/bin.d.mts +1 -1
  93. package/dist/types/shadow/yarn/bin.d.mts.map +1 -1
  94. package/dist/types/utils/agent.d.mts.map +1 -1
  95. package/dist/types/utils/alerts-map.d.mts.map +1 -1
  96. package/dist/types/utils/api.d.mts.map +1 -1
  97. package/dist/types/utils/cmd.d.mts.map +1 -1
  98. package/dist/types/utils/coana.d.mts.map +1 -1
  99. package/dist/types/utils/color-or-markdown.d.mts.map +1 -1
  100. package/dist/types/utils/config.d.mts.map +1 -1
  101. package/dist/types/utils/cve-to-ghsa.d.mts.map +1 -1
  102. package/dist/types/utils/debug.d.mts +45 -0
  103. package/dist/types/utils/debug.d.mts.map +1 -0
  104. package/dist/types/utils/determine-org-slug.d.mts.map +1 -1
  105. package/dist/types/utils/dlx.d.mts +1 -1
  106. package/dist/types/utils/dlx.d.mts.map +1 -1
  107. package/dist/types/utils/ecosystem.d.mts.map +1 -1
  108. package/dist/types/utils/errors.d.mts +48 -0
  109. package/dist/types/utils/errors.d.mts.map +1 -1
  110. package/dist/types/utils/filter-config.d.mts.map +1 -1
  111. package/dist/types/utils/fs.d.mts.map +1 -1
  112. package/dist/types/utils/get-output-kind.d.mts.map +1 -1
  113. package/dist/types/utils/git.d.mts.map +1 -1
  114. package/dist/types/utils/github.d.mts.map +1 -1
  115. package/dist/types/utils/markdown.d.mts +17 -0
  116. package/dist/types/utils/markdown.d.mts.map +1 -1
  117. package/dist/types/utils/meow-with-subcommands.d.mts.map +1 -1
  118. package/dist/types/utils/npm-package-arg.d.mts +5 -1
  119. package/dist/types/utils/npm-package-arg.d.mts.map +1 -1
  120. package/dist/types/utils/npm-paths.d.mts.map +1 -1
  121. package/dist/types/utils/npm-spec.d.mts +57 -0
  122. package/dist/types/utils/npm-spec.d.mts.map +1 -0
  123. package/dist/types/utils/output-formatting.d.mts.map +1 -1
  124. package/dist/types/utils/package-environment.d.mts.map +1 -1
  125. package/dist/types/utils/pnpm-paths.d.mts.map +1 -1
  126. package/dist/types/utils/purl-to-ghsa.d.mts.map +1 -1
  127. package/dist/types/utils/purl.d.mts +24 -0
  128. package/dist/types/utils/purl.d.mts.map +1 -1
  129. package/dist/types/utils/requirements.d.mts.map +1 -1
  130. package/dist/types/utils/sdk.d.mts.map +1 -1
  131. package/dist/types/utils/serialize-result-json.d.mts.map +1 -1
  132. package/dist/types/utils/socket-json.d.mts.map +1 -1
  133. package/dist/types/utils/socket-package-alert.d.mts.map +1 -1
  134. package/dist/types/utils/socket-url.d.mts.map +1 -1
  135. package/dist/types/utils/strings.d.mts +12 -0
  136. package/dist/types/utils/strings.d.mts.map +1 -1
  137. package/dist/types/utils/terminal-link.d.mts +45 -0
  138. package/dist/types/utils/terminal-link.d.mts.map +1 -0
  139. package/dist/types/utils/tildify.d.mts +0 -2
  140. package/dist/types/utils/tildify.d.mts.map +1 -1
  141. package/dist/types/utils/yarn-paths.d.mts.map +1 -1
  142. package/dist/types/utils/yarn-version.d.mts.map +1 -1
  143. package/dist/utils.js +1393 -453
  144. package/dist/utils.js.map +1 -1
  145. package/dist/vendor.js +682 -682
  146. package/package.json +3 -3
  147. package/shadow-bin/npm +2 -2
  148. package/shadow-bin/npx +2 -2
  149. package/shadow-bin/pnpm +2 -2
  150. package/shadow-bin/yarn +2 -2
package/dist/utils.js CHANGED
@@ -18,17 +18,263 @@ var prompts = require('../external/@socketsecurity/registry/lib/prompts');
18
18
  var spawn = require('../external/@socketsecurity/registry/lib/spawn');
19
19
  var fs = require('../external/@socketsecurity/registry/lib/fs');
20
20
  var require$$5 = require('node:module');
21
- var shadowNpmBin = require('./shadow-npm-bin.js');
22
21
  var fs$1 = require('node:fs');
23
22
  var require$$13 = require('../external/@socketsecurity/registry/lib/url');
24
- var promises = require('node:timers/promises');
25
23
  var agent = require('../external/@socketsecurity/registry/lib/agent');
26
24
  var bin = require('../external/@socketsecurity/registry/lib/bin');
27
25
  var packages = require('../external/@socketsecurity/registry/lib/packages');
26
+ var promises = require('node:timers/promises');
28
27
  var globs = require('../external/@socketsecurity/registry/lib/globs');
29
28
  var streams = require('../external/@socketsecurity/registry/lib/streams');
30
29
 
31
30
  var _documentCurrentScript = typeof document !== 'undefined' ? document.currentScript : null;
31
+ /**
32
+ * Debug utilities for Socket CLI.
33
+ * Provides structured debugging with categorized levels and helpers.
34
+ *
35
+ * Debug Categories:
36
+ * DEFAULT (shown with SOCKET_CLI_DEBUG=1):
37
+ * - 'error': Critical errors that prevent operation
38
+ * - 'warn': Important warnings that may affect behavior
39
+ * - 'notice': Notable events and state changes
40
+ * - 'silly': Very verbose debugging info
41
+ *
42
+ * OPT-IN ONLY (require explicit DEBUG='category' even with SOCKET_CLI_DEBUG=1):
43
+ * - 'inspect': Detailed object inspection (DEBUG='inspect' or DEBUG='*')
44
+ * - 'stdio': Command execution logs (DEBUG='stdio' or DEBUG='*')
45
+ *
46
+ * These opt-in categories are intentionally excluded from default debug output
47
+ * to reduce noise. Enable them explicitly when needed for deep debugging.
48
+ */
49
+
50
+
51
+ /**
52
+ * Debug an API response.
53
+ * Logs essential info without exposing sensitive data.
54
+ */
55
+ function debugApiResponse(endpoint, status, error) {
56
+ if (error) {
57
+ require$$9.debugDir('error', {
58
+ endpoint,
59
+ error: error instanceof Error ? error.message : 'Unknown error'
60
+ });
61
+ } else if (status && status >= 400) {
62
+ require$$9.debugFn('warn', `API ${endpoint}: HTTP ${status}`);
63
+ } else if (require$$9.isDebug('notice')) {
64
+ require$$9.debugFn('notice', `API ${endpoint}: ${status || 'pending'}`);
65
+ }
66
+ }
67
+
68
+ /**
69
+ * Debug file operation.
70
+ * Logs file operations with appropriate level.
71
+ */
72
+ function debugFileOp(operation, filepath, error) {
73
+ if (error) {
74
+ require$$9.debugDir('warn', {
75
+ operation,
76
+ filepath,
77
+ error: error instanceof Error ? error.message : 'Unknown error'
78
+ });
79
+ } else if (require$$9.isDebug('silly')) {
80
+ require$$9.debugFn('silly', `File ${operation}: ${filepath}`);
81
+ }
82
+ }
83
+
84
+ /**
85
+ * Debug package scanning.
86
+ * Provides insight into security scanning.
87
+ */
88
+ function debugScan(phase, packageCount, details) {
89
+ switch (phase) {
90
+ case 'start':
91
+ if (packageCount) {
92
+ require$$9.debugFn('notice', `Scanning ${packageCount} packages`);
93
+ }
94
+ break;
95
+ case 'progress':
96
+ if (require$$9.isDebug('silly') && packageCount) {
97
+ require$$9.debugFn('silly', `Scan progress: ${packageCount} packages processed`);
98
+ }
99
+ break;
100
+ case 'complete':
101
+ require$$9.debugFn('notice', `Scan complete${packageCount ? `: ${packageCount} packages` : ''}`);
102
+ break;
103
+ case 'error':
104
+ require$$9.debugDir('error', {
105
+ phase: 'scan_error',
106
+ details
107
+ });
108
+ break;
109
+ }
110
+ }
111
+
112
+ /**
113
+ * Debug configuration loading.
114
+ */
115
+ function debugConfig(source, found, error) {
116
+ if (error) {
117
+ require$$9.debugDir('warn', {
118
+ source,
119
+ error: error instanceof Error ? error.message : 'Unknown error'
120
+ });
121
+ } else if (found) {
122
+ require$$9.debugFn('notice', `Config loaded: ${source}`);
123
+ } else if (require$$9.isDebug('silly')) {
124
+ require$$9.debugFn('silly', `Config not found: ${source}`);
125
+ }
126
+ }
127
+
128
+ /**
129
+ * Debug git operations.
130
+ * Only logs important git operations, not every command.
131
+ */
132
+ function debugGit(operation, success, details) {
133
+ if (!success) {
134
+ require$$9.debugDir('warn', {
135
+ git_op: operation,
136
+ ...details
137
+ });
138
+ } else if (require$$9.isDebug('notice') && operation.includes('push') || operation.includes('commit')) {
139
+ // Only log important operations like push and commit.
140
+ require$$9.debugFn('notice', `Git ${operation} succeeded`);
141
+ } else if (require$$9.isDebug('silly')) {
142
+ require$$9.debugFn('silly', `Git ${operation}`);
143
+ }
144
+ }
145
+
146
+ /**
147
+ * Error utilities for Socket CLI.
148
+ * Provides consistent error handling, formatting, and message extraction.
149
+ *
150
+ * Key Classes:
151
+ * - AuthError: Authentication failures (401/403 responses)
152
+ * - InputError: User input validation failures
153
+ *
154
+ * Key Functions:
155
+ * - captureException: Send errors to Sentry for monitoring
156
+ * - formatErrorWithDetail: Format errors with detailed context
157
+ * - getErrorCause: Get error cause with fallback to UNKNOWN_ERROR
158
+ * - getErrorMessage: Extract error message from any thrown value
159
+ *
160
+ * Error Handling Strategy:
161
+ * - Always prefer specific error types over generic errors
162
+ * - Use formatErrorWithDetail for user-facing error messages
163
+ * - Log errors to Sentry in production for monitoring
164
+ */
165
+
166
+ const {
167
+ kInternalsSymbol,
168
+ [kInternalsSymbol]: {
169
+ getSentry
170
+ }
171
+ } = constants.default;
172
+ class AuthError extends Error {}
173
+ class InputError extends Error {
174
+ constructor(message, body) {
175
+ super(message);
176
+ this.body = body;
177
+ }
178
+ }
179
+ async function captureException(exception, hint) {
180
+ const result = captureExceptionSync(exception, hint);
181
+ // "Sleep" for a second, just in case, hopefully enough time to initiate fetch.
182
+ await promises.setTimeout(1000);
183
+ return result;
184
+ }
185
+ function captureExceptionSync(exception, hint) {
186
+ const Sentry = getSentry();
187
+ if (!Sentry) {
188
+ return '';
189
+ }
190
+ require$$9.debugFn('notice', 'send: exception to Sentry');
191
+ return Sentry.captureException(exception, hint);
192
+ }
193
+
194
+ /**
195
+ * Extracts an error message from an unknown value.
196
+ * Returns the message if it's an Error object, otherwise returns undefined.
197
+ *
198
+ * @param error - The error object to extract message from
199
+ * @returns The error message or undefined
200
+ */
201
+ function getErrorMessage(error) {
202
+ return error?.message;
203
+ }
204
+
205
+ /**
206
+ * Extracts an error message from an unknown value with a fallback.
207
+ * Returns the message if it's an Error object, otherwise returns the fallback.
208
+ *
209
+ * @param error - The error object to extract message from
210
+ * @param fallback - The fallback message if no error message is found
211
+ * @returns The error message or fallback
212
+ *
213
+ * @example
214
+ * getErrorMessageOr(error, 'Unknown error occurred')
215
+ * // Returns: "ENOENT: no such file or directory" or "Unknown error occurred"
216
+ */
217
+ function getErrorMessageOr(error, fallback) {
218
+ return getErrorMessage(error) || fallback;
219
+ }
220
+
221
+ /**
222
+ * Extracts an error cause from an unknown value.
223
+ * Returns the error message if available, otherwise UNKNOWN_ERROR.
224
+ * Commonly used for creating CResult error causes.
225
+ *
226
+ * @param error - The error object to extract message from
227
+ * @returns The error message or UNKNOWN_ERROR constant
228
+ *
229
+ * @example
230
+ * return { ok: false, message: 'Operation failed', cause: getErrorCause(e) }
231
+ */
232
+ function getErrorCause(error) {
233
+ return getErrorMessageOr(error, constants.UNKNOWN_ERROR);
234
+ }
235
+
236
+ /**
237
+ * Formats an error message with an optional error detail appended.
238
+ * Extracts the message from an unknown error value and appends it
239
+ * to the base message if available.
240
+ *
241
+ * @param baseMessage - The base message to display
242
+ * @param error - The error object to extract message from
243
+ * @returns Formatted message with error detail if available
244
+ *
245
+ * @example
246
+ * formatErrorWithDetail('Failed to delete file', error)
247
+ * // Returns: "Failed to delete file: ENOENT: no such file or directory"
248
+ * // Or just: "Failed to delete file" if no error message
249
+ */
250
+ function formatErrorWithDetail(baseMessage, error) {
251
+ const errorMessage = getErrorMessage(error);
252
+ return `${baseMessage}${errorMessage ? `: ${errorMessage}` : ''}`;
253
+ }
254
+
255
+ /**
256
+ * Configuration utilities for Socket CLI.
257
+ * Manages CLI configuration including API tokens, org settings, and preferences.
258
+ *
259
+ * Configuration Hierarchy (highest priority first):
260
+ * 1. Environment variables (SOCKET_CLI_*)
261
+ * 2. Command-line --config flag
262
+ * 3. Persisted config file (base64 encoded JSON)
263
+ *
264
+ * Supported Config Keys:
265
+ * - apiBaseUrl: Socket API endpoint URL
266
+ * - apiProxy: Proxy for API requests
267
+ * - apiToken: Authentication token for Socket API
268
+ * - defaultOrg/org: Default organization slug
269
+ * - enforcedOrgs: Organizations with enforced security policies
270
+ *
271
+ * Key Functions:
272
+ * - findSocketYmlSync: Locate socket.yml configuration file
273
+ * - getConfigValue: Retrieve configuration value by key
274
+ * - overrideCachedConfig: Apply temporary config overrides
275
+ * - updateConfigValue: Persist configuration changes
276
+ */
277
+
32
278
  const sensitiveConfigKeyLookup = new Set([constants.CONFIG_KEY_API_TOKEN]);
33
279
  const supportedConfig = new Map([[constants.CONFIG_KEY_API_BASE_URL, 'Base URL of the Socket API endpoint'], [constants.CONFIG_KEY_API_PROXY, 'A proxy through which to access the Socket API'], [constants.CONFIG_KEY_API_TOKEN, 'The Socket API token required to access most Socket API endpoints'], [constants.CONFIG_KEY_DEFAULT_ORG, 'The default org slug to use; usually the org your Socket API token has access to. When set, all orgSlug arguments are implied to be this value.'], [constants.CONFIG_KEY_ENFORCED_ORGS, 'Orgs in this list have their security policies enforced on this machine'], ['skipAskToPersistDefaultOrg', 'This flag prevents the Socket CLI from asking you to persist the org slug when you selected one interactively'], [constants.CONFIG_KEY_ORG, 'Alias for defaultOrg']]);
34
280
  const supportedConfigEntries = [...supportedConfig.entries()].sort((a, b) => sorts.naturalCompare(a[0], b[0]));
@@ -45,8 +291,10 @@ function getConfigValues() {
45
291
  if (raw) {
46
292
  try {
47
293
  Object.assign(_cachedConfig, JSON.parse(Buffer.from(raw, 'base64').toString()));
48
- } catch {
294
+ debugConfig(socketAppDataPath, true);
295
+ } catch (e) {
49
296
  logger.logger.warn(`Failed to parse config at ${socketAppDataPath}`);
297
+ debugConfig(socketAppDataPath, false, e);
50
298
  }
51
299
  // Normalize apiKey to apiToken and persist it.
52
300
  // This is a one time migration per user.
@@ -100,13 +348,12 @@ function findSocketYmlSync(dir = process.cwd()) {
100
348
  }
101
349
  };
102
350
  } catch (e) {
103
- require$$9.debugDir('inspect', {
104
- error: e
105
- });
351
+ require$$9.debugFn('error', `Failed to parse config file: ${ymlPath}`);
352
+ require$$9.debugDir('error', e);
106
353
  return {
107
354
  ok: false,
108
355
  message: `Found file but was unable to parse ${ymlPath}`,
109
- cause: e instanceof Error ? e.message : String(e)
356
+ cause: getErrorCause(e)
110
357
  };
111
358
  }
112
359
  }
@@ -267,6 +514,20 @@ function updateConfigValue(configKey, value) {
267
514
  };
268
515
  }
269
516
 
517
+ /**
518
+ * Requirements configuration utilities for Socket CLI.
519
+ * Manages API permissions and quota requirements for commands.
520
+ *
521
+ * Key Functions:
522
+ * - getRequirements: Load requirements configuration
523
+ * - getRequirementsKey: Convert command path to requirements key
524
+ *
525
+ * Configuration:
526
+ * - Loads from requirements.json
527
+ * - Maps command paths to permission requirements
528
+ * - Used for permission validation and help text
529
+ */
530
+
270
531
  const require$3 = require$$5.createRequire((typeof document === 'undefined' ? require('u' + 'rl').pathToFileURL(__filename).href : (_documentCurrentScript && _documentCurrentScript.tagName.toUpperCase() === 'SCRIPT' && _documentCurrentScript.src || new URL('utils.js', document.baseURI).href)));
271
532
  let _requirements;
272
533
  function getRequirements() {
@@ -283,6 +544,32 @@ function getRequirementsKey(cmdPath) {
283
544
  return cmdPath.replace(/^socket[: ]/, '').replace(/ +/g, ':');
284
545
  }
285
546
 
547
+ /**
548
+ * Socket SDK utilities for Socket CLI.
549
+ * Manages SDK initialization and configuration for API communication.
550
+ *
551
+ * Authentication:
552
+ * - Interactive password prompt for missing tokens
553
+ * - Supports environment variable (SOCKET_CLI_API_TOKEN)
554
+ * - Validates token format and presence
555
+ *
556
+ * Proxy Support:
557
+ * - Automatic proxy agent selection
558
+ * - HTTP/HTTPS proxy configuration
559
+ * - Respects SOCKET_CLI_API_PROXY environment variable
560
+ *
561
+ * SDK Setup:
562
+ * - createSocketSdk: Create configured SDK instance
563
+ * - getDefaultApiToken: Retrieve API token from config/env
564
+ * - getDefaultProxyUrl: Retrieve proxy URL from config/env
565
+ * - getPublicApiToken: Get public API token constant
566
+ * - setupSdk: Initialize Socket SDK with authentication
567
+ *
568
+ * User Agent:
569
+ * - Automatic user agent generation from package.json
570
+ * - Includes CLI version and platform information
571
+ */
572
+
286
573
  const TOKEN_PREFIX = 'sktsec_';
287
574
  const TOKEN_PREFIX_LENGTH = TOKEN_PREFIX.length;
288
575
  const TOKEN_VISIBLE_LENGTH = 5;
@@ -375,6 +662,27 @@ async function setupSdk(options) {
375
662
  };
376
663
  }
377
664
 
665
+ /**
666
+ * API utilities for Socket CLI.
667
+ * Provides consistent API communication with error handling and permissions management.
668
+ *
669
+ * Key Functions:
670
+ * - getDefaultApiBaseUrl: Get configured API endpoint
671
+ * - getErrorMessageForHttpStatusCode: User-friendly HTTP error messages
672
+ * - handleApiCall: Execute Socket SDK API calls with error handling
673
+ * - handleApiCallNoSpinner: Execute API calls without UI spinner
674
+ * - queryApi: Execute raw API queries with text response
675
+ *
676
+ * Error Handling:
677
+ * - Automatic permission requirement logging for 403 errors
678
+ * - Detailed error messages for common HTTP status codes
679
+ * - Integration with debug helpers for API response logging
680
+ *
681
+ * Configuration:
682
+ * - Respects SOCKET_CLI_API_BASE_URL environment variable
683
+ * - Falls back to configured apiBaseUrl or default API_V0_URL
684
+ */
685
+
378
686
  const NO_ERROR_MESSAGE = 'No error message returned';
379
687
  /**
380
688
  * Get command requirements from requirements.json based on command path.
@@ -469,13 +777,10 @@ async function handleApiCall(value, options) {
469
777
  };
470
778
  if (description) {
471
779
  logger.logger.fail(`An error was thrown while requesting ${description}`);
472
- require$$9.debugFn('error', `caught: ${description} error`);
780
+ debugApiResponse(description, undefined, e);
473
781
  } else {
474
- require$$9.debugFn('error', `caught: Socket API request error`);
782
+ debugApiResponse('Socket API', undefined, e);
475
783
  }
476
- require$$9.debugDir('inspect', {
477
- error: e
478
- });
479
784
  require$$9.debugDir('inspect', {
480
785
  socketSdkErrorResult
481
786
  });
@@ -484,7 +789,8 @@ async function handleApiCall(value, options) {
484
789
 
485
790
  // Note: TS can't narrow down the type of result due to generics.
486
791
  if (sdkResult.success === false) {
487
- require$$9.debugFn('error', `fail:${description ? ` ${description}` : ''} bad response`);
792
+ const endpoint = description || 'Socket API';
793
+ debugApiResponse(endpoint, sdkResult.status);
488
794
  require$$9.debugDir('inspect', {
489
795
  sdkResult
490
796
  });
@@ -519,10 +825,8 @@ async function handleApiCallNoSpinner(value, description) {
519
825
  try {
520
826
  sdkResult = await value;
521
827
  } catch (e) {
522
- require$$9.debugFn('error', `caught: ${description} error`);
523
- require$$9.debugDir('inspect', {
524
- error: e
525
- });
828
+ require$$9.debugFn('error', `API request failed: ${description}`);
829
+ require$$9.debugDir('error', e);
526
830
  const errStr = e ? String(e).trim() : '';
527
831
  const message = 'Socket API error';
528
832
  const rawCause = errStr || NO_ERROR_MESSAGE;
@@ -604,10 +908,8 @@ async function queryApiSafeText(path, description, commandPath) {
604
908
  if (description) {
605
909
  spinner.failAndStop(`An error was thrown while requesting ${description}.`);
606
910
  }
607
- require$$9.debugFn('error', 'caught: await queryApi() error');
608
- require$$9.debugDir('inspect', {
609
- error: e
610
- });
911
+ require$$9.debugFn('error', 'Query API request failed');
912
+ require$$9.debugDir('error', e);
611
913
  const errStr = e ? String(e).trim() : '';
612
914
  const message = 'API request failed';
613
915
  const rawCause = errStr || NO_ERROR_MESSAGE;
@@ -640,10 +942,8 @@ async function queryApiSafeText(path, description, commandPath) {
640
942
  data
641
943
  };
642
944
  } catch (e) {
643
- require$$9.debugFn('error', 'caught: await result.text() error');
644
- require$$9.debugDir('inspect', {
645
- error: e
646
- });
945
+ require$$9.debugFn('error', 'Failed to read API response text');
946
+ require$$9.debugDir('error', e);
647
947
  return {
648
948
  ok: false,
649
949
  message: 'API request failed',
@@ -728,10 +1028,8 @@ async function sendApiRequest(path, options) {
728
1028
  if (description) {
729
1029
  spinner.failAndStop(`An error was thrown while requesting ${description}.`);
730
1030
  }
731
- require$$9.debugFn('error', `caught: await fetch() ${method} error`);
732
- require$$9.debugDir('inspect', {
733
- error: e
734
- });
1031
+ require$$9.debugFn('error', `API ${method} request failed`);
1032
+ require$$9.debugDir('error', e);
735
1033
  const errStr = e ? String(e).trim() : '';
736
1034
  const message = 'API request failed';
737
1035
  const rawCause = errStr || NO_ERROR_MESSAGE;
@@ -768,10 +1066,8 @@ async function sendApiRequest(path, options) {
768
1066
  data: data
769
1067
  };
770
1068
  } catch (e) {
771
- require$$9.debugFn('error', 'caught: await result.json() error');
772
- require$$9.debugDir('inspect', {
773
- error: e
774
- });
1069
+ require$$9.debugFn('error', 'Failed to parse API response JSON');
1070
+ require$$9.debugDir('error', e);
775
1071
  return {
776
1072
  ok: false,
777
1073
  message: 'API request failed',
@@ -786,6 +1082,24 @@ function failMsgWithBadge(badge, message) {
786
1082
  return `${prefix}${postfix}`;
787
1083
  }
788
1084
 
1085
+ /**
1086
+ * Markdown utilities for Socket CLI.
1087
+ * Generates formatted markdown output for reports and documentation.
1088
+ *
1089
+ * Key Functions:
1090
+ * - mdTableStringNumber: Create markdown table with string keys and number values
1091
+ *
1092
+ * Table Features:
1093
+ * - Auto-sizing columns based on content
1094
+ * - Proper alignment for headers and data
1095
+ * - Clean markdown-compliant formatting
1096
+ *
1097
+ * Usage:
1098
+ * - Analytics reports
1099
+ * - Scan result tables
1100
+ * - Statistical summaries
1101
+ */
1102
+
789
1103
  function mdTableStringNumber(title1, title2, obj) {
790
1104
  // | Date | Counts |
791
1105
  // | ----------- | ------ |
@@ -904,9 +1218,8 @@ function serializeResultJson(data) {
904
1218
  process.exitCode = 1;
905
1219
  const message = 'There was a problem converting the data set to JSON. Please try again without --json';
906
1220
  logger.logger.fail(message);
907
- require$$9.debugDir('inspect', {
908
- error: e
909
- });
1221
+ require$$9.debugFn('error', 'JSON serialization failed');
1222
+ require$$9.debugDir('error', e);
910
1223
 
911
1224
  // This could be caused by circular references, which is an "us" problem.
912
1225
  return `${JSON.stringify({
@@ -917,6 +1230,82 @@ function serializeResultJson(data) {
917
1230
  }
918
1231
  }
919
1232
 
1233
+ /**
1234
+ * Creates a terminal link to a local file.
1235
+ * @param filePath The file path to link to
1236
+ * @param text Optional display text (defaults to the file path itself)
1237
+ * @returns A terminal link to the file
1238
+ */
1239
+ function fileLink(filePath, text) {
1240
+ const absolutePath = path.isAbsolute(filePath) ? filePath : path.resolve(filePath);
1241
+ return vendor.terminalLinkExports(filePath, `file://${absolutePath}`);
1242
+ }
1243
+
1244
+ /**
1245
+ * Creates a terminal link to an email address.
1246
+ * @param email The email address
1247
+ * @param text Optional display text (defaults to the email address itself)
1248
+ * @returns A terminal link to compose an email
1249
+ */
1250
+ function mailtoLink(email, text) {
1251
+ return vendor.terminalLinkExports(email, `mailto:${email}`);
1252
+ }
1253
+
1254
+ /**
1255
+ * Creates a terminal link to a web URL.
1256
+ * @param url The web URL to link to
1257
+ * @param text Optional display text (defaults to the URL itself)
1258
+ * @returns A terminal link to the URL
1259
+ */
1260
+ function webLink(url, text) {
1261
+ return vendor.terminalLinkExports(text ?? url, url);
1262
+ }
1263
+
1264
+ /**
1265
+ * Creates a terminal link to the Socket.dev dashboard.
1266
+ * @param path The path within the dashboard (e.g., '/org/YOURORG/alerts')
1267
+ * @param text Optional display text
1268
+ * @returns A terminal link to the Socket.dev dashboard URL
1269
+ */
1270
+ function socketDashboardLink(dashPath, text) {
1271
+ const url = `https://socket.dev/dashboard${dashPath.startsWith('/') ? dashPath : `/${dashPath}`}`;
1272
+ return vendor.terminalLinkExports(text, url);
1273
+ }
1274
+
1275
+ /**
1276
+ * Creates a terminal link to Socket.dev documentation.
1277
+ * @param docPath The documentation path (e.g., '/docs/api-keys')
1278
+ * @param text Optional display text
1279
+ * @returns A terminal link to the Socket.dev documentation
1280
+ */
1281
+ function socketDocsLink(docPath, text) {
1282
+ const url = `https://docs.socket.dev${docPath.startsWith('/') ? docPath : `/${docPath}`}`;
1283
+ return vendor.terminalLinkExports(text ?? url, url);
1284
+ }
1285
+
1286
+ /**
1287
+ * Creates a terminal link to Socket.dev package page.
1288
+ * @param ecosystem The package ecosystem (e.g., 'npm')
1289
+ * @param packageName The package name
1290
+ * @param version Optional package version or path (e.g., 'files/1.0.0/CHANGELOG.md')
1291
+ * @param text Optional display text
1292
+ * @returns A terminal link to the Socket.dev package page
1293
+ */
1294
+ function socketPackageLink(ecosystem, packageName, version, text) {
1295
+ let url;
1296
+ if (version) {
1297
+ // Check if version contains a path like 'files/1.0.0/CHANGELOG.md'.
1298
+ if (version.includes('/')) {
1299
+ url = `https://socket.dev/${ecosystem}/package/${packageName}/${version}`;
1300
+ } else {
1301
+ url = `https://socket.dev/${ecosystem}/package/${packageName}/overview/${version}`;
1302
+ }
1303
+ } else {
1304
+ url = `https://socket.dev/${ecosystem}/package/${packageName}`;
1305
+ }
1306
+ return vendor.terminalLinkExports(text, url);
1307
+ }
1308
+
920
1309
  function checkCommandInput(outputKind, ...checks) {
921
1310
  if (checks.every(d => d.test)) {
922
1311
  return true;
@@ -965,6 +1354,24 @@ function checkCommandInput(outputKind, ...checks) {
965
1354
  return false;
966
1355
  }
967
1356
 
1357
+ /**
1358
+ * Output format detection utilities for Socket CLI.
1359
+ * Determines output format based on command flags.
1360
+ *
1361
+ * Key Functions:
1362
+ * - getOutputKind: Determine output format from flags
1363
+ *
1364
+ * Supported Formats:
1365
+ * - JSON: Machine-readable JSON output
1366
+ * - Markdown: Formatted markdown for reports
1367
+ * - Text: Plain text for terminal display
1368
+ *
1369
+ * Usage:
1370
+ * - Processes --json and --markdown flags
1371
+ * - Returns appropriate output format constant
1372
+ * - Defaults to text format for terminal display
1373
+ */
1374
+
968
1375
  function getOutputKind(json, markdown) {
969
1376
  if (json) {
970
1377
  return constants.OUTPUT_JSON;
@@ -975,10 +1382,44 @@ function getOutputKind(json, markdown) {
975
1382
  return constants.OUTPUT_TEXT;
976
1383
  }
977
1384
 
1385
+ /**
1386
+ * String manipulation utilities for Socket CLI.
1387
+ * Provides common string transformations and formatting.
1388
+ *
1389
+ * Key Functions:
1390
+ * - camelToKebab: Convert camelCase to kebab-case
1391
+ *
1392
+ * Usage:
1393
+ * - Command name transformations
1394
+ * - Flag name conversions
1395
+ * - Consistent string formatting
1396
+ */
1397
+
978
1398
  function camelToKebab(str) {
979
1399
  return str === '' ? '' : str.replace(/([a-z])([A-Z])/g, '$1-$2').toLowerCase();
980
1400
  }
981
1401
 
1402
+ /**
1403
+ * Output formatting utilities for Socket CLI.
1404
+ * Provides consistent formatting for help text and command output.
1405
+ *
1406
+ * Key Functions:
1407
+ * - getFlagApiRequirementsOutput: Format API requirements for flags
1408
+ * - getHelpListOutput: Format help text lists with descriptions
1409
+ * - getFlagsHelpOutput: Generate formatted help for command flags
1410
+ *
1411
+ * Formatting Features:
1412
+ * - Automatic indentation and alignment
1413
+ * - Flag description formatting
1414
+ * - Requirements and permissions display
1415
+ * - Hidden flag filtering
1416
+ *
1417
+ * Usage:
1418
+ * - Used by command help systems
1419
+ * - Provides consistent terminal output formatting
1420
+ * - Handles kebab-case conversion for flags
1421
+ */
1422
+
982
1423
  function getFlagApiRequirementsOutput(cmdPath, options) {
983
1424
  const {
984
1425
  indent = 6
@@ -1049,8 +1490,19 @@ function getHelpListOutput(list, options) {
1049
1490
  return result.trim() || '(none)';
1050
1491
  }
1051
1492
 
1052
- // Replace the start of a path with ~/ when it starts with your home dir.
1053
- // A common way to abbreviate the user home dir (though not strictly posix).
1493
+ /**
1494
+ * Path tildification utilities for Socket CLI.
1495
+ * Abbreviates home directory paths with tilde notation.
1496
+ *
1497
+ * Key Functions:
1498
+ * - tildify: Replace home directory with ~ in paths
1499
+ *
1500
+ * Usage:
1501
+ * - Shortens absolute paths for display
1502
+ * - Converts /Users/name/... to ~/...
1503
+ * - Common Unix convention for home directory
1504
+ */
1505
+
1054
1506
  function tildify(cwd) {
1055
1507
  return cwd.replace(new RegExp(`^${regexps.escapeRegExp(constants.default.homePath)}(?:${path.sep}|$)`, 'i'), '~/');
1056
1508
  }
@@ -1269,10 +1721,15 @@ async function meowWithSubcommands(subcommands, options) {
1269
1721
  // We want to detect whether a bool flag is given at all.
1270
1722
  booleanDefault: undefined
1271
1723
  });
1272
- const noSpinner = cli1.flags['spinner'] === false;
1273
- const orgFlag = String(cli1.flags['org'] || '') || undefined;
1724
+ const {
1725
+ config: configFlag,
1726
+ org: orgFlag,
1727
+ spinner: spinnerFlag
1728
+ } = cli1.flags;
1729
+ const noSpinner = spinnerFlag === false || require$$9.isDebug();
1274
1730
 
1275
- // Use CI spinner style when --no-spinner is passed.
1731
+ // Use CI spinner style when --no-spinner is passed or debug mode is enabled.
1732
+ // This prevents the spinner from interfering with debug output.
1276
1733
  if (noSpinner) {
1277
1734
  constants.default.spinner.spinner = spinner.getCliSpinners('ci');
1278
1735
  }
@@ -1282,8 +1739,8 @@ async function meowWithSubcommands(subcommands, options) {
1282
1739
  let configOverrideResult;
1283
1740
  if (constants.default.ENV.SOCKET_CLI_CONFIG) {
1284
1741
  configOverrideResult = overrideCachedConfig(constants.default.ENV.SOCKET_CLI_CONFIG);
1285
- } else if (cli1.flags['config']) {
1286
- configOverrideResult = overrideCachedConfig(cli1.flags['config']);
1742
+ } else if (configFlag) {
1743
+ configOverrideResult = overrideCachedConfig(configFlag);
1287
1744
  }
1288
1745
  if (constants.default.ENV.SOCKET_CLI_NO_API_TOKEN) {
1289
1746
  // This overrides the config override and even the explicit token env var.
@@ -1479,9 +1936,10 @@ function meowOrExit({
1479
1936
  spinner: spinnerFlag,
1480
1937
  version: versionFlag
1481
1938
  } = cli.flags;
1482
- const noSpinner = spinnerFlag === false;
1939
+ const noSpinner = spinnerFlag === false || require$$9.isDebug();
1483
1940
 
1484
1941
  // Use CI spinner style when --no-spinner is passed.
1942
+ // This prevents the spinner from interfering with debug output.
1485
1943
  if (noSpinner) {
1486
1944
  constants.default.spinner.spinner = spinner.getCliSpinners('ci');
1487
1945
  }
@@ -1520,6 +1978,8 @@ function meowOrExit({
1520
1978
  console.error('Unknown flag\n--version');
1521
1979
  // eslint-disable-next-line n/no-process-exit
1522
1980
  process.exit(2);
1981
+ // This line is never reached in production, but helps tests.
1982
+ throw new Error('process.exit called');
1523
1983
  }
1524
1984
 
1525
1985
  // Now test for help state. Run Meow again. If it exits now, it must be due
@@ -1683,7 +2143,7 @@ async function determineOrgSlug(orgFlag, interactive, dryRun) {
1683
2143
  logger.logger.warn('');
1684
2144
  logger.logger.warn('Note: When running in CI, you probably want to set the `--org` flag.');
1685
2145
  logger.logger.warn('');
1686
- logger.logger.warn('For details, see: https://docs.socket.dev/docs/v1-migration-guide');
2146
+ logger.logger.warn(`For details, see the ${webLink(constants.V1_MIGRATION_GUIDE_URL, 'v1 migration guide')}`);
1687
2147
  logger.logger.warn('');
1688
2148
  logger.logger.warn('This command will exit now because the org slug is required to proceed.');
1689
2149
  return ['', undefined];
@@ -1753,6 +2213,33 @@ async function getDefaultOrgSlug() {
1753
2213
  };
1754
2214
  }
1755
2215
 
2216
+ /**
2217
+ * Git utilities for Socket CLI.
2218
+ * Provides git operations for repository management, branch handling, and commits.
2219
+ *
2220
+ * Branch Operations:
2221
+ * - gitCheckoutBranch: Switch to branch
2222
+ * - gitCreateBranch: Create new local branch
2223
+ * - gitDeleteBranch: Delete local branch
2224
+ * - gitDeleteRemoteBranch: Delete remote branch
2225
+ * - gitPushBranch: Push branch to remote with --force
2226
+ *
2227
+ * Commit Operations:
2228
+ * - gitCleanFdx: Remove untracked files
2229
+ * - gitCommit: Stage files and create commit
2230
+ * - gitEnsureIdentity: Configure git user.name/email
2231
+ * - gitResetHard: Reset to branch/commit
2232
+ *
2233
+ * Remote URL Parsing:
2234
+ * - parseGitRemoteUrl: Extract owner/repo from SSH or HTTPS URLs
2235
+ *
2236
+ * Repository Information:
2237
+ * - detectDefaultBranch: Find default branch (main/master/develop/etc)
2238
+ * - getBaseBranch: Determine base branch (respects GitHub Actions env)
2239
+ * - getRepoInfo: Extract owner/repo from git remote URL
2240
+ * - gitBranch: Get current branch or commit hash
2241
+ */
2242
+
1756
2243
  // Listed in order of check preference.
1757
2244
  const COMMON_DEFAULT_BRANCH_NAMES = [
1758
2245
  // Modern default (GitHub, GitLab, Bitbucket have switched to this).
@@ -1796,22 +2283,21 @@ async function getBaseBranch(cwd = process.cwd()) {
1796
2283
  }
1797
2284
  async function getRepoInfo(cwd = process.cwd()) {
1798
2285
  let info;
1799
- const quotedCmd = '`git remote get-url origin`';
1800
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1801
2286
  try {
1802
2287
  const remoteUrl = (await spawn.spawn('git', ['remote', 'get-url', 'origin'], {
1803
2288
  cwd
1804
2289
  })).stdout;
1805
2290
  info = parseGitRemoteUrl(remoteUrl);
1806
2291
  if (!info) {
1807
- require$$9.debugFn('error', 'git: unmatched git remote URL format');
1808
- require$$9.debugDir('inspect', {
2292
+ require$$9.debugFn('warn', `Unmatched git remote URL format: ${remoteUrl}`);
2293
+ require$$9.debugDir('warn', {
1809
2294
  remoteUrl
1810
2295
  });
1811
2296
  }
1812
2297
  } catch (e) {
1813
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2298
+ // Expected failure when not in a git repo.
1814
2299
  require$$9.debugDir('inspect', {
2300
+ message: 'git remote get-url failed',
1815
2301
  error: e
1816
2302
  });
1817
2303
  }
@@ -1825,41 +2311,29 @@ async function gitBranch(cwd = process.cwd()) {
1825
2311
  const stdioPipeOptions = {
1826
2312
  cwd
1827
2313
  };
1828
- let quotedCmd = '`git symbolic-ref --short HEAD`';
1829
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1830
2314
  // Try symbolic-ref first which returns the branch name or fails in a
1831
2315
  // detached HEAD state.
1832
2316
  try {
1833
2317
  const gitSymbolicRefResult = await spawn.spawn('git', ['symbolic-ref', '--short', 'HEAD'], stdioPipeOptions);
1834
- require$$9.debugDir('stdio', {
1835
- gitSymbolicRefResult
1836
- });
1837
2318
  return gitSymbolicRefResult.stdout;
1838
2319
  } catch (e) {
1839
- if (require$$9.isDebug('stdio')) {
1840
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1841
- require$$9.debugDir('inspect', {
1842
- error: e
1843
- });
1844
- }
2320
+ // Expected in detached HEAD state, fallback to rev-parse.
2321
+ require$$9.debugDir('inspect', {
2322
+ message: 'In detached HEAD state',
2323
+ error: e
2324
+ });
1845
2325
  }
1846
2326
  // Fallback to using rev-parse to get the short commit hash in a
1847
2327
  // detached HEAD state.
1848
- quotedCmd = '`git rev-parse --short HEAD`';
1849
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1850
2328
  try {
1851
2329
  const gitRevParseResult = await spawn.spawn('git', ['rev-parse', '--short', 'HEAD'], stdioPipeOptions);
1852
- require$$9.debugDir('stdio', {
1853
- gitRevParseResult
1854
- });
1855
2330
  return gitRevParseResult.stdout;
1856
2331
  } catch (e) {
1857
- if (require$$9.isDebug('stdio')) {
1858
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1859
- require$$9.debugDir('inspect', {
1860
- error: e
1861
- });
1862
- }
2332
+ // Both methods failed, likely not in a git repo.
2333
+ require$$9.debugDir('inspect', {
2334
+ message: 'Unable to determine git branch',
2335
+ error: e
2336
+ });
1863
2337
  }
1864
2338
  return undefined;
1865
2339
  }
@@ -1890,14 +2364,12 @@ async function gitCleanFdx(cwd = process.cwd()) {
1890
2364
  cwd,
1891
2365
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
1892
2366
  };
1893
- const quotedCmd = '`git clean -fdx`';
1894
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1895
2367
  try {
1896
2368
  await spawn.spawn('git', ['clean', '-fdx'], stdioIgnoreOptions);
2369
+ debugGit('clean -fdx', true);
1897
2370
  return true;
1898
2371
  } catch (e) {
1899
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1900
- require$$9.debugDir('inspect', {
2372
+ debugGit('clean -fdx', false, {
1901
2373
  error: e
1902
2374
  });
1903
2375
  }
@@ -1908,14 +2380,12 @@ async function gitCheckoutBranch(branch, cwd = process.cwd()) {
1908
2380
  cwd,
1909
2381
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
1910
2382
  };
1911
- const quotedCmd = `\`git checkout ${branch}\``;
1912
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1913
2383
  try {
1914
2384
  await spawn.spawn('git', ['checkout', branch], stdioIgnoreOptions);
2385
+ debugGit(`checkout ${branch}`, true);
1915
2386
  return true;
1916
2387
  } catch (e) {
1917
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1918
- require$$9.debugDir('inspect', {
2388
+ debugGit(`checkout ${branch}`, false, {
1919
2389
  error: e
1920
2390
  });
1921
2391
  }
@@ -1929,14 +2399,12 @@ async function gitCreateBranch(branch, cwd = process.cwd()) {
1929
2399
  cwd,
1930
2400
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
1931
2401
  };
1932
- const quotedCmd = `\`git branch ${branch}\``;
1933
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1934
2402
  try {
1935
2403
  await spawn.spawn('git', ['branch', branch], stdioIgnoreOptions);
2404
+ debugGit(`branch ${branch}`, true);
1936
2405
  return true;
1937
2406
  } catch (e) {
1938
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1939
- require$$9.debugDir('inspect', {
2407
+ debugGit(`branch ${branch}`, false, {
1940
2408
  error: e
1941
2409
  });
1942
2410
  }
@@ -1947,19 +2415,22 @@ async function gitPushBranch(branch, cwd = process.cwd()) {
1947
2415
  cwd,
1948
2416
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
1949
2417
  };
1950
- const quotedCmd = `\`git push --force --set-upstream origin ${branch}\``;
1951
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
1952
2418
  try {
1953
2419
  await spawn.spawn('git', ['push', '--force', '--set-upstream', 'origin', branch], stdioIgnoreOptions);
2420
+ debugGit(`push ${branch}`, true);
1954
2421
  return true;
1955
2422
  } catch (e) {
1956
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
1957
2423
  if (spawn.isSpawnError(e) && e.code === 128) {
1958
- require$$9.debugFn('error', "denied: token requires write permissions for 'contents' and 'pull-requests'");
2424
+ require$$9.debugFn('error', "Push denied: token requires write permissions for 'contents' and 'pull-requests'");
2425
+ require$$9.debugDir('error', e);
2426
+ require$$9.debugDir('inspect', {
2427
+ branch
2428
+ });
2429
+ } else {
2430
+ debugGit(`push ${branch}`, false, {
2431
+ error: e
2432
+ });
1959
2433
  }
1960
- require$$9.debugDir('inspect', {
1961
- error: e
1962
- });
1963
2434
  }
1964
2435
  return false;
1965
2436
  }
@@ -1981,26 +2452,31 @@ async function gitCommit(commitMsg, filepaths, options) {
1981
2452
  cwd,
1982
2453
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
1983
2454
  };
1984
- const quotedAddCmd = `\`git add ${filepaths.join(' ')}\``;
1985
- require$$9.debugFn('stdio', `spawn: ${quotedAddCmd}`);
1986
2455
  try {
1987
2456
  await spawn.spawn('git', ['add', ...filepaths], stdioIgnoreOptions);
2457
+ debugGit('add', true, {
2458
+ count: filepaths.length
2459
+ });
1988
2460
  } catch (e) {
1989
- require$$9.debugFn('error', `caught: ${quotedAddCmd} failed`);
1990
- require$$9.debugDir('inspect', {
2461
+ debugGit('add', false, {
1991
2462
  error: e
1992
2463
  });
2464
+ require$$9.debugDir('inspect', {
2465
+ filepaths
2466
+ });
2467
+ return false;
1993
2468
  }
1994
- const quotedCommitCmd = `\`git commit -m ${commitMsg}\``;
1995
- require$$9.debugFn('stdio', `spawn: ${quotedCommitCmd}`);
1996
2469
  try {
1997
2470
  await spawn.spawn('git', ['commit', '-m', commitMsg], stdioIgnoreOptions);
2471
+ debugGit('commit', true);
1998
2472
  return true;
1999
2473
  } catch (e) {
2000
- require$$9.debugFn('error', `caught: ${quotedCommitCmd} failed`);
2001
- require$$9.debugDir('inspect', {
2474
+ debugGit('commit', false, {
2002
2475
  error: e
2003
2476
  });
2477
+ require$$9.debugDir('inspect', {
2478
+ commitMsg
2479
+ });
2004
2480
  }
2005
2481
  return false;
2006
2482
  }
@@ -2009,19 +2485,16 @@ async function gitDeleteBranch(branch, cwd = process.cwd()) {
2009
2485
  cwd,
2010
2486
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
2011
2487
  };
2012
- const quotedCmd = `\`git branch -D ${branch}\``;
2013
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2014
2488
  try {
2015
2489
  // Will throw with exit code 1 if branch does not exist.
2016
2490
  await spawn.spawn('git', ['branch', '-D', branch], stdioIgnoreOptions);
2017
2491
  return true;
2018
2492
  } catch (e) {
2019
- if (require$$9.isDebug('stdio')) {
2020
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2021
- require$$9.debugDir('inspect', {
2022
- error: e
2023
- });
2024
- }
2493
+ // Expected failure when branch doesn't exist.
2494
+ require$$9.debugDir('inspect', {
2495
+ message: `Branch deletion failed (may not exist): ${branch}`,
2496
+ error: e
2497
+ });
2025
2498
  }
2026
2499
  return false;
2027
2500
  }
@@ -2035,41 +2508,30 @@ async function gitEnsureIdentity(name, email, cwd = process.cwd()) {
2035
2508
  1: value
2036
2509
  }) => {
2037
2510
  let configValue;
2038
- {
2039
- const quotedCmd = `\`git config --get ${prop}\``;
2040
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2041
- try {
2042
- // Will throw with exit code 1 if the config property is not set.
2043
- const gitConfigResult = await spawn.spawn('git', ['config', '--get', prop], stdioPipeOptions);
2044
- require$$9.debugDir('stdio', {
2045
- gitConfigResult
2046
- });
2047
- configValue = gitConfigResult.stdout;
2048
- } catch (e) {
2049
- if (require$$9.isDebug('stdio')) {
2050
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2051
- require$$9.debugDir('inspect', {
2052
- error: e
2053
- });
2054
- }
2055
- }
2511
+ try {
2512
+ // Will throw with exit code 1 if the config property is not set.
2513
+ const gitConfigResult = await spawn.spawn('git', ['config', '--get', prop], stdioPipeOptions);
2514
+ configValue = gitConfigResult.stdout;
2515
+ } catch (e) {
2516
+ // Expected when config property is not set.
2517
+ require$$9.debugDir('inspect', {
2518
+ message: `Git config property not set: ${prop}`,
2519
+ error: e
2520
+ });
2056
2521
  }
2057
2522
  if (configValue !== value) {
2058
2523
  const stdioIgnoreOptions = {
2059
2524
  cwd,
2060
2525
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
2061
2526
  };
2062
- const quotedCmd = `\`git config ${prop} ${value}\``;
2063
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2064
2527
  try {
2065
2528
  await spawn.spawn('git', ['config', prop, value], stdioIgnoreOptions);
2066
2529
  } catch (e) {
2067
- if (require$$9.isDebug('stdio')) {
2068
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2069
- require$$9.debugDir('inspect', {
2070
- error: e
2071
- });
2072
- }
2530
+ require$$9.debugFn('warn', `Failed to set git config: ${prop}`);
2531
+ require$$9.debugDir('warn', e);
2532
+ require$$9.debugDir('inspect', {
2533
+ value
2534
+ });
2073
2535
  }
2074
2536
  }
2075
2537
  }));
@@ -2079,19 +2541,12 @@ async function gitLocalBranchExists(branch, cwd = process.cwd()) {
2079
2541
  cwd,
2080
2542
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
2081
2543
  };
2082
- const quotedCmd = `\`git show-ref --quiet refs/heads/${branch}\``;
2083
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2084
2544
  try {
2085
2545
  // Will throw with exit code 1 if the branch does not exist.
2086
2546
  await spawn.spawn('git', ['show-ref', constants.FLAG_QUIET, `refs/heads/${branch}`], stdioIgnoreOptions);
2087
2547
  return true;
2088
- } catch (e) {
2089
- if (require$$9.isDebug('stdio')) {
2090
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2091
- require$$9.debugDir('inspect', {
2092
- error: e
2093
- });
2094
- }
2548
+ } catch {
2549
+ // Expected when branch doesn't exist - no logging needed.
2095
2550
  }
2096
2551
  return false;
2097
2552
  }
@@ -2099,21 +2554,15 @@ async function gitRemoteBranchExists(branch, cwd = process.cwd()) {
2099
2554
  const stdioPipeOptions = {
2100
2555
  cwd
2101
2556
  };
2102
- const quotedCmd = `\`git ls-remote --heads origin ${branch}\``;
2103
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2104
2557
  try {
2105
2558
  const lsRemoteResult = await spawn.spawn('git', ['ls-remote', '--heads', 'origin', branch], stdioPipeOptions);
2106
- require$$9.debugDir('stdio', {
2107
- lsRemoteResult
2108
- });
2109
2559
  return lsRemoteResult.stdout.length > 0;
2110
2560
  } catch (e) {
2111
- if (require$$9.isDebug('stdio')) {
2112
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2113
- require$$9.debugDir('inspect', {
2114
- error: e
2115
- });
2116
- }
2561
+ // Expected when remote is not accessible or branch doesn't exist.
2562
+ require$$9.debugDir('inspect', {
2563
+ message: `Remote branch check failed: ${branch}`,
2564
+ error: e
2565
+ });
2117
2566
  }
2118
2567
  return false;
2119
2568
  }
@@ -2128,14 +2577,12 @@ async function gitResetHard(branch = 'HEAD', cwd = process.cwd()) {
2128
2577
  cwd,
2129
2578
  stdio: require$$9.isDebug('stdio') ? 'inherit' : 'ignore'
2130
2579
  };
2131
- const quotedCmd = `\`git reset --hard ${branch}\``;
2132
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2133
2580
  try {
2134
2581
  await spawn.spawn('git', ['reset', '--hard', branch], stdioIgnoreOptions);
2582
+ debugGit(`reset --hard ${branch}`, true);
2135
2583
  return true;
2136
2584
  } catch (e) {
2137
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2138
- require$$9.debugDir('inspect', {
2585
+ debugGit(`reset --hard ${branch}`, false, {
2139
2586
  error: e
2140
2587
  });
2141
2588
  }
@@ -2145,13 +2592,8 @@ async function gitUnstagedModifiedFiles(cwd = process.cwd()) {
2145
2592
  const stdioPipeOptions = {
2146
2593
  cwd
2147
2594
  };
2148
- const quotedCmd = `\`git diff --name-only\``;
2149
- require$$9.debugFn('stdio', `spawn: ${quotedCmd}`);
2150
2595
  try {
2151
2596
  const gitDiffResult = await spawn.spawn('git', ['diff', '--name-only'], stdioPipeOptions);
2152
- require$$9.debugDir('stdio', {
2153
- gitDiffResult
2154
- });
2155
2597
  const changedFilesDetails = gitDiffResult.stdout;
2156
2598
  const relPaths = changedFilesDetails.split('\n');
2157
2599
  return {
@@ -2159,10 +2601,8 @@ async function gitUnstagedModifiedFiles(cwd = process.cwd()) {
2159
2601
  data: relPaths.map(p => path$1.normalizePath(p))
2160
2602
  };
2161
2603
  } catch (e) {
2162
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
2163
- require$$9.debugDir('inspect', {
2164
- error: e
2165
- });
2604
+ require$$9.debugFn('error', 'Failed to get unstaged modified files');
2605
+ require$$9.debugDir('error', e);
2166
2606
  return {
2167
2607
  ok: false,
2168
2608
  message: 'Git Error',
@@ -2210,6 +2650,72 @@ function parseGitRemoteUrl(remoteUrl) {
2210
2650
  } : result;
2211
2651
  }
2212
2652
 
2653
+ /**
2654
+ * Package URL (PURL) utilities for Socket CLI.
2655
+ * Implements the PURL specification for universal package identification.
2656
+ *
2657
+ * PURL Format:
2658
+ * pkg:type/namespace/name@version?qualifiers#subpath
2659
+ *
2660
+ * Key Functions:
2661
+ * - createPurlObject: Create PURL from components
2662
+ * - isPurl: Check if string is valid PURL
2663
+ * - normalizePurl: Normalize PURL format
2664
+ * - parsePurl: Parse PURL string to object
2665
+ * - purlToString: Convert PURL object to string
2666
+ *
2667
+ * Supported Types:
2668
+ * - cargo: Rust packages
2669
+ * - gem: Ruby packages
2670
+ * - go: Go modules
2671
+ * - maven: Java packages
2672
+ * - npm: Node.js packages
2673
+ * - pypi: Python packages
2674
+ *
2675
+ * See: https://github.com/package-url/purl-spec
2676
+ */
2677
+
2678
+ function createPurlObject(type, name, options) {
2679
+ let opts;
2680
+ if (require$$11.isObjectObject(type)) {
2681
+ opts = {
2682
+ __proto__: null,
2683
+ ...type
2684
+ };
2685
+ type = opts.type;
2686
+ name = opts.name;
2687
+ } else if (require$$11.isObjectObject(name)) {
2688
+ opts = {
2689
+ __proto__: null,
2690
+ ...name
2691
+ };
2692
+ name = opts.name;
2693
+ } else {
2694
+ opts = {
2695
+ __proto__: null,
2696
+ ...options
2697
+ };
2698
+ if (typeof name !== 'string') {
2699
+ name = opts.name;
2700
+ }
2701
+ }
2702
+ const {
2703
+ namespace,
2704
+ qualifiers,
2705
+ subpath,
2706
+ throws,
2707
+ version
2708
+ } = opts;
2709
+ const shouldThrow = throws === undefined || !!throws;
2710
+ try {
2711
+ return new vendor.packageurlJsExports.PackageURL(type, namespace, name, version, qualifiers, subpath);
2712
+ } catch (e) {
2713
+ if (shouldThrow) {
2714
+ throw e;
2715
+ }
2716
+ }
2717
+ return undefined;
2718
+ }
2213
2719
  function getPurlObject(purl, options) {
2214
2720
  const {
2215
2721
  throws
@@ -2231,6 +2737,26 @@ function normalizePurl(rawPurl) {
2231
2737
  return rawPurl.startsWith('pkg:') ? rawPurl : `pkg:${rawPurl}`;
2232
2738
  }
2233
2739
 
2740
+ /**
2741
+ * Socket.dev URL utilities for Socket CLI.
2742
+ * Generates URLs for Socket.dev website features and resources.
2743
+ *
2744
+ * Key Functions:
2745
+ * - getPkgFullNameFromPurl: Extract full package name from PURL
2746
+ * - getSocketDevAlertUrl: Generate alert type documentation URL
2747
+ * - getSocketDevPackageOverviewUrl: Generate package overview URL
2748
+ * - getSocketDevPackageOverviewUrlFromPurl: Generate overview URL from PURL
2749
+ * - getSocketDevPackageUrl: Generate package detail URL
2750
+ * - getSocketDevPackageUrlFromPurl: Generate package URL from PURL
2751
+ * - getSocketDevReportUrl: Generate scan report URL
2752
+ *
2753
+ * URL Generation:
2754
+ * - Package overview and detail pages
2755
+ * - Security alert documentation
2756
+ * - Scan report links
2757
+ * - Ecosystem-specific URL formatting
2758
+ */
2759
+
2234
2760
  function getPkgFullNameFromPurl(purl) {
2235
2761
  const purlObj = getPurlObject(purl);
2236
2762
  const {
@@ -2273,6 +2799,19 @@ function* walkNestedMap(map, keys = []) {
2273
2799
  }
2274
2800
  }
2275
2801
 
2802
+ /**
2803
+ * Coana integration utilities for Socket CLI.
2804
+ * Manages reachability analysis via Coana tech CLI.
2805
+ *
2806
+ * Key Functions:
2807
+ * - extractTier1ReachabilityScanId: Extract scan ID from socket facts file
2808
+ *
2809
+ * Integration:
2810
+ * - Works with @coana-tech/cli for reachability analysis
2811
+ * - Processes socket facts JSON files
2812
+ * - Extracts tier 1 reachability scan identifiers
2813
+ */
2814
+
2276
2815
  function extractTier1ReachabilityScanId(socketFactsFile) {
2277
2816
  const json = fs.readJsonSync(socketFactsFile, {
2278
2817
  throws: false
@@ -2281,6 +2820,25 @@ function extractTier1ReachabilityScanId(socketFactsFile) {
2281
2820
  return tier1ReachabilityScanId.length > 0 ? tier1ReachabilityScanId : undefined;
2282
2821
  }
2283
2822
 
2823
+ /**
2824
+ * File system utilities for Socket CLI.
2825
+ * Provides file and directory search functionality.
2826
+ *
2827
+ * Key Functions:
2828
+ * - findUp: Search for files/directories up the directory tree
2829
+ *
2830
+ * Features:
2831
+ * - Upward directory traversal
2832
+ * - Supports file and directory searching
2833
+ * - Abort signal support for cancellation
2834
+ * - Multiple name search support
2835
+ *
2836
+ * Usage:
2837
+ * - Finding configuration files (package.json, lockfiles)
2838
+ * - Locating project root directories
2839
+ * - Searching for specific files in parent directories
2840
+ */
2841
+
2284
2842
  async function findUp(name, options) {
2285
2843
  const opts = {
2286
2844
  __proto__: null,
@@ -2622,13 +3180,15 @@ function exitWithBinPathError$2(binName) {
2622
3180
  // could not be found.
2623
3181
  // eslint-disable-next-line n/no-process-exit
2624
3182
  process.exit(127);
3183
+ // This line is never reached in production, but helps tests.
3184
+ throw new Error('process.exit called');
2625
3185
  }
2626
3186
  let _yarnBinPath;
2627
3187
  function getYarnBinPath() {
2628
3188
  if (_yarnBinPath === undefined) {
2629
3189
  _yarnBinPath = getYarnBinPathDetails().path;
2630
3190
  if (!_yarnBinPath) {
2631
- exitWithBinPathError$2(constants.default.YARN);
3191
+ exitWithBinPathError$2(constants.YARN);
2632
3192
  }
2633
3193
  }
2634
3194
  return _yarnBinPath;
@@ -2636,7 +3196,7 @@ function getYarnBinPath() {
2636
3196
  let _yarnBinPathDetails;
2637
3197
  function getYarnBinPathDetails() {
2638
3198
  if (_yarnBinPathDetails === undefined) {
2639
- _yarnBinPathDetails = findBinPathDetailsSync(constants.default.YARN);
3199
+ _yarnBinPathDetails = findBinPathDetailsSync(constants.YARN);
2640
3200
  }
2641
3201
  return _yarnBinPathDetails;
2642
3202
  }
@@ -2651,6 +3211,9 @@ function isYarnBerry() {
2651
3211
  const yarnBinPath = getYarnBinPath();
2652
3212
  const result = spawn.spawnSync(yarnBinPath, ['--version'], {
2653
3213
  encoding: 'utf8',
3214
+ // On Windows, yarn is often a .cmd file that requires shell execution.
3215
+ // The spawn function from @socketsecurity/registry will handle this properly
3216
+ // when shell is true.
2654
3217
  shell: constants.default.WIN32
2655
3218
  });
2656
3219
  if (result.status === 0 && result.stdout) {
@@ -2668,202 +3231,25 @@ function isYarnBerry() {
2668
3231
  return _isYarnBerry;
2669
3232
  }
2670
3233
 
2671
- function exitWithBinPathError$1(binName) {
2672
- logger.logger.fail(`Socket unable to locate ${binName}; ensure it is available in the PATH environment variable`);
2673
- // The exit code 127 indicates that the command or binary being executed
2674
- // could not be found.
2675
- // eslint-disable-next-line n/no-process-exit
2676
- process.exit(127);
2677
- }
2678
- let _npmBinPath;
2679
- function getNpmBinPath() {
2680
- if (_npmBinPath === undefined) {
2681
- _npmBinPath = getNpmBinPathDetails().path;
2682
- if (!_npmBinPath) {
2683
- exitWithBinPathError$1(constants.NPM);
2684
- }
2685
- }
2686
- return _npmBinPath;
2687
- }
2688
- let _npmBinPathDetails;
2689
- function getNpmBinPathDetails() {
2690
- if (_npmBinPathDetails === undefined) {
2691
- _npmBinPathDetails = findBinPathDetailsSync(constants.NPM);
2692
- }
2693
- return _npmBinPathDetails;
2694
- }
2695
- let _npmDirPath;
2696
- function getNpmDirPath() {
2697
- if (_npmDirPath === undefined) {
2698
- const npmBinPath = getNpmBinPath();
2699
- _npmDirPath = npmBinPath ? findNpmDirPathSync(npmBinPath) : undefined;
2700
- if (!_npmDirPath) {
2701
- _npmDirPath = constants.default.ENV.SOCKET_CLI_NPM_PATH || undefined;
2702
- }
2703
- if (!_npmDirPath) {
2704
- let message = 'Unable to find npm CLI install directory.';
2705
- if (npmBinPath) {
2706
- message += `\nSearched parent directories of ${path.dirname(npmBinPath)}.`;
2707
- }
2708
- message += '\n\nThis is may be a bug with socket-npm related to changes to the npm CLI.';
2709
- message += `\nPlease report to ${constants.default.SOCKET_CLI_ISSUES_URL}.`;
2710
- logger.logger.fail(message);
2711
- // The exit code 127 indicates that the command or binary being executed
2712
- // could not be found.
2713
- // eslint-disable-next-line n/no-process-exit
2714
- process.exit(127);
2715
- }
2716
- }
2717
- return _npmDirPath;
2718
- }
2719
- let _npmRequire;
2720
- function getNpmRequire() {
2721
- if (_npmRequire === undefined) {
2722
- const npmDirPath = getNpmDirPath();
2723
- const npmNmPath = path.join(npmDirPath, `${constants.NODE_MODULES}/npm`);
2724
- _npmRequire = require$$5.createRequire(path.join(fs$1.existsSync(npmNmPath) ? npmNmPath : npmDirPath, '<dummy-basename>'));
2725
- }
2726
- return _npmRequire;
2727
- }
2728
- let _npxBinPath;
2729
- function getNpxBinPath() {
2730
- if (_npxBinPath === undefined) {
2731
- _npxBinPath = getNpxBinPathDetails().path;
2732
- if (!_npxBinPath) {
2733
- exitWithBinPathError$1('npx');
2734
- }
2735
- }
2736
- return _npxBinPath;
2737
- }
2738
- let _npxBinPathDetails;
2739
- function getNpxBinPathDetails() {
2740
- if (_npxBinPathDetails === undefined) {
2741
- _npxBinPathDetails = findBinPathDetailsSync('npx');
2742
- }
2743
- return _npxBinPathDetails;
2744
- }
2745
- function isNpmBinPathShadowed() {
2746
- return getNpmBinPathDetails().shadowed;
2747
- }
2748
- function isNpxBinPathShadowed() {
2749
- return getNpxBinPathDetails().shadowed;
2750
- }
2751
-
2752
- const helpFlags = new Set([constants.FLAG_HELP, '-h']);
2753
-
2754
- /**
2755
- * Convert command arguments to a properly formatted string representation.
2756
- */
2757
- function cmdFlagsToString(args) {
2758
- const result = [];
2759
- for (let i = 0, {
2760
- length
2761
- } = args; i < length; i += 1) {
2762
- const arg = args[i].trim();
2763
- if (arg.startsWith('--')) {
2764
- const nextArg = i + 1 < length ? args[i + 1].trim() : undefined;
2765
- // Check if the next item exists and is NOT another flag.
2766
- if (nextArg && !nextArg.startsWith('--')) {
2767
- result.push(`${arg}=${nextArg}`);
2768
- i += 1;
2769
- } else {
2770
- result.push(arg);
2771
- }
2772
- }
2773
- }
2774
- return result.join(' ');
2775
- }
2776
-
2777
- /**
2778
- * Convert flag values to array format for processing.
2779
- */
2780
- function cmdFlagValueToArray(value) {
2781
- if (typeof value === 'string') {
2782
- return value.trim().split(/, */).filter(Boolean);
2783
- }
2784
- if (Array.isArray(value)) {
2785
- return value.flatMap(cmdFlagValueToArray);
2786
- }
2787
- return [];
2788
- }
2789
-
2790
- /**
2791
- * Add command name prefix to message text.
2792
- */
2793
- function cmdPrefixMessage(cmdName, text) {
2794
- const cmdPrefix = cmdName ? `${cmdName}: ` : '';
2795
- return `${cmdPrefix}${text}`;
2796
- }
2797
-
2798
3234
  /**
2799
- * Filter out Socket flags from argv before passing to subcommands.
3235
+ * DLX execution utilities for Socket CLI.
3236
+ * Manages package execution via npx/pnpm dlx/yarn dlx commands.
3237
+ *
3238
+ * Key Functions:
3239
+ * - spawnCdxgenDlx: Execute CycloneDX generator via dlx
3240
+ * - spawnCoanaDlx: Execute Coana CLI tool via dlx
3241
+ * - spawnDlx: Execute packages using dlx-style commands
3242
+ * - spawnSynpDlx: Execute Synp converter via dlx
3243
+ *
3244
+ * Package Manager Detection:
3245
+ * - Auto-detects npm, pnpm, or yarn based on lockfiles
3246
+ * - Supports force-refresh and silent execution modes
3247
+ *
3248
+ * Integration:
3249
+ * - Works with shadow binaries for security scanning
3250
+ * - Handles version pinning and cache management
3251
+ * - Configures environment for third-party tools
2800
3252
  */
2801
- function filterFlags(argv, flagsToFilter, exceptions) {
2802
- const filtered = [];
2803
-
2804
- // Build set of flags to filter from the provided flag objects.
2805
- const flagsToFilterSet = new Set();
2806
- const flagsWithValueSet = new Set();
2807
- for (const [flagName, flag] of Object.entries(flagsToFilter)) {
2808
- const longFlag = `--${camelToKebab(flagName)}`;
2809
- // Special case for negated booleans.
2810
- if (flagName === 'spinner' || flagName === 'banner') {
2811
- flagsToFilterSet.add(`--no-${flagName}`);
2812
- } else {
2813
- flagsToFilterSet.add(longFlag);
2814
- }
2815
- if (flag?.shortFlag) {
2816
- flagsToFilterSet.add(`-${flag.shortFlag}`);
2817
- }
2818
- // Track flags that take values.
2819
- if (flag.type !== 'boolean') {
2820
- flagsWithValueSet.add(longFlag);
2821
- if (flag?.shortFlag) {
2822
- flagsWithValueSet.add(`-${flag.shortFlag}`);
2823
- }
2824
- }
2825
- }
2826
- for (let i = 0, {
2827
- length
2828
- } = argv; i < length; i += 1) {
2829
- const arg = argv[i];
2830
- // Check if this flag should be kept as an exception.
2831
- if (exceptions?.includes(arg)) {
2832
- filtered.push(arg);
2833
- // Handle flags that take values.
2834
- if (flagsWithValueSet.has(arg)) {
2835
- // Include the next argument (the flag value).
2836
- i += 1;
2837
- if (i < length) {
2838
- filtered.push(argv[i]);
2839
- }
2840
- }
2841
- } else if (flagsToFilterSet.has(arg)) {
2842
- // Skip flags that take values.
2843
- if (flagsWithValueSet.has(arg)) {
2844
- // Skip the next argument (the flag value).
2845
- i += 1;
2846
- }
2847
- // Skip boolean flags (no additional argument to skip).
2848
- } else if (arg && Array.from(flagsWithValueSet).some(flag => arg.startsWith(`${flag}=`))) {
2849
- // Skip --flag=value format for Socket flags unless it's an exception.
2850
- if (exceptions?.some(exc => arg.startsWith(`${exc}=`))) {
2851
- filtered.push(arg);
2852
- }
2853
- // Otherwise skip it.
2854
- } else {
2855
- filtered.push(arg);
2856
- }
2857
- }
2858
- return filtered;
2859
- }
2860
-
2861
- /**
2862
- * Check if argument is a help flag.
2863
- */
2864
- function isHelpFlag(cmdArg) {
2865
- return helpFlags.has(cmdArg);
2866
- }
2867
3253
 
2868
3254
  const require$2 = require$$5.createRequire((typeof document === 'undefined' ? require('u' + 'rl').pathToFileURL(__filename).href : (_documentCurrentScript && _documentCurrentScript.tagName.toUpperCase() === 'SCRIPT' && _documentCurrentScript.src || new URL('utils.js', document.baseURI).href)));
2869
3255
  const {
@@ -2919,10 +3305,8 @@ async function spawnDlx(packageSpec, args, options, spawnExtra) {
2919
3305
  const packageString = `${packageSpec.name}@${packageSpec.version}`;
2920
3306
 
2921
3307
  // Build command args based on package manager.
2922
- let binName;
2923
3308
  let spawnArgs;
2924
3309
  if (pm === constants.PNPM) {
2925
- binName = constants.PNPM;
2926
3310
  spawnArgs = ['dlx'];
2927
3311
  if (force) {
2928
3312
  // For pnpm, set dlx-cache-max-age to 0 via env to force fresh download.
@@ -2949,7 +3333,6 @@ async function spawnDlx(packageSpec, args, options, spawnExtra) {
2949
3333
  const shadowPnpmBin = /*@__PURE__*/require$2(constants.default.shadowPnpmBinPath);
2950
3334
  return await shadowPnpmBin(spawnArgs, finalShadowOptions, spawnExtra);
2951
3335
  } else if (pm === constants.YARN && isYarnBerry()) {
2952
- binName = constants.YARN;
2953
3336
  spawnArgs = ['dlx'];
2954
3337
  // Yarn dlx runs in a temporary environment by design and should always fetch fresh.
2955
3338
  if (silent) {
@@ -2961,7 +3344,6 @@ async function spawnDlx(packageSpec, args, options, spawnExtra) {
2961
3344
  } else {
2962
3345
  // Use npm exec/npx.
2963
3346
  // For consistency, we'll use npx which is more commonly used for one-off execution.
2964
- binName = 'npx';
2965
3347
  spawnArgs = ['--yes'];
2966
3348
  if (force) {
2967
3349
  // Use --force to bypass cache and get latest within range.
@@ -2971,7 +3353,8 @@ async function spawnDlx(packageSpec, args, options, spawnExtra) {
2971
3353
  spawnArgs.push(constants.FLAG_SILENT);
2972
3354
  }
2973
3355
  spawnArgs.push(packageString, ...args);
2974
- return await shadowNpmBin(binName, spawnArgs, finalShadowOptions, spawnExtra);
3356
+ const shadowNpxBin = /*@__PURE__*/require$2(constants.default.shadowNpxBinPath);
3357
+ return await shadowNpxBin(spawnArgs, finalShadowOptions, spawnExtra);
2975
3358
  }
2976
3359
  }
2977
3360
 
@@ -3036,8 +3419,8 @@ async function spawnCoanaDlx(args, orgSlug, options, spawnExtra) {
3036
3419
  };
3037
3420
  } catch (e) {
3038
3421
  const stderr = e?.stderr;
3039
- const cause = e?.message || constants.UNKNOWN_ERROR;
3040
- const message = stderr ? stderr : cause;
3422
+ const cause = getErrorCause(e);
3423
+ const message = stderr || cause;
3041
3424
  return {
3042
3425
  ok: false,
3043
3426
  data: e,
@@ -3084,6 +3467,26 @@ function hasEnterpriseOrgPlan(orgs) {
3084
3467
  return orgs.some(o => o.plan === 'enterprise');
3085
3468
  }
3086
3469
 
3470
+ /**
3471
+ * Socket JSON utilities for Socket CLI.
3472
+ * Manages .socket/socket.json configuration and scan metadata.
3473
+ *
3474
+ * Key Functions:
3475
+ * - loadDotSocketDirectory: Load .socket directory configuration
3476
+ * - saveSocketJson: Persist scan configuration to .socket/socket.json
3477
+ * - validateSocketJson: Validate socket.json structure
3478
+ *
3479
+ * File Structure:
3480
+ * - Contains scan metadata and configuration
3481
+ * - Stores scan IDs and repository information
3482
+ * - Tracks CLI version and scan timestamps
3483
+ *
3484
+ * Directory Management:
3485
+ * - Creates .socket directory as needed
3486
+ * - Handles nested directory structures
3487
+ * - Supports both read and write operations
3488
+ */
3489
+
3087
3490
  function readOrDefaultSocketJson(cwd) {
3088
3491
  const jsonCResult = readSocketJsonSync(cwd, true);
3089
3492
  return jsonCResult.ok ? jsonCResult.data :
@@ -3129,35 +3532,31 @@ function readSocketJsonSync(cwd, defaultOnError = false) {
3129
3532
  } catch (e) {
3130
3533
  if (defaultOnError) {
3131
3534
  logger.logger.warn(`Failed to read ${constants.SOCKET_JSON}, using default`);
3132
- require$$9.debugDir('inspect', {
3133
- error: e
3134
- });
3535
+ require$$9.debugFn('warn', `Failed to read ${constants.SOCKET_JSON} sync`);
3536
+ require$$9.debugDir('warn', e);
3135
3537
  return {
3136
3538
  ok: true,
3137
3539
  data: getDefaultSocketJson()
3138
3540
  };
3139
3541
  }
3140
- const cause = e?.message;
3141
- require$$9.debugDir('inspect', {
3142
- error: e
3143
- });
3542
+ const cause = formatErrorWithDetail(`An error occurred while trying to read ${constants.SOCKET_JSON}`, e);
3543
+ require$$9.debugFn('error', `Failed to read ${constants.SOCKET_JSON} sync`);
3544
+ require$$9.debugDir('error', e);
3144
3545
  return {
3145
3546
  ok: false,
3146
3547
  message: `Failed to read ${constants.SOCKET_JSON}`,
3147
- cause: `An error occurred while trying to read ${constants.SOCKET_JSON}${cause ? `: ${cause}` : ''}`
3548
+ cause
3148
3549
  };
3149
3550
  }
3150
3551
  let jsonObj;
3151
3552
  try {
3152
3553
  jsonObj = JSON.parse(jsonContent);
3153
3554
  } catch (e) {
3154
- require$$9.debugFn('error', 'caught: JSON.parse error');
3555
+ require$$9.debugFn('error', `Failed to parse ${constants.SOCKET_JSON} as JSON (sync)`);
3155
3556
  require$$9.debugDir('inspect', {
3156
3557
  jsonContent
3157
3558
  });
3158
- require$$9.debugDir('inspect', {
3159
- error: e
3160
- });
3559
+ require$$9.debugDir('error', e);
3161
3560
  if (defaultOnError) {
3162
3561
  logger.logger.warn(`Failed to parse ${constants.SOCKET_JSON}, using default`);
3163
3562
  return {
@@ -3191,11 +3590,11 @@ async function writeSocketJson(cwd, sockJson) {
3191
3590
  try {
3192
3591
  jsonContent = JSON.stringify(sockJson, null, 2);
3193
3592
  } catch (e) {
3194
- require$$9.debugFn('error', 'caught: JSON.stringify error');
3593
+ require$$9.debugFn('error', `Failed to serialize ${constants.SOCKET_JSON} to JSON`);
3195
3594
  require$$9.debugDir('inspect', {
3196
- error: e,
3197
3595
  sockJson
3198
3596
  });
3597
+ require$$9.debugDir('error', e);
3199
3598
  return {
3200
3599
  ok: false,
3201
3600
  message: 'Failed to serialize to JSON',
@@ -3210,6 +3609,32 @@ async function writeSocketJson(cwd, sockJson) {
3210
3609
  };
3211
3610
  }
3212
3611
 
3612
+ /**
3613
+ * GitHub utilities for Socket CLI.
3614
+ * Provides GitHub API integration for repository operations and GHSA vulnerability data.
3615
+ *
3616
+ * Authentication:
3617
+ * - getGitHubToken: Retrieve GitHub token from env/git config
3618
+ * - getOctokit: Get authenticated Octokit instance
3619
+ * - getOctokitGraphql: Get authenticated GraphQL client
3620
+ *
3621
+ * Caching:
3622
+ * - 5-minute TTL for API responses
3623
+ * - Automatic cache invalidation
3624
+ * - Persistent cache in node_modules/.cache
3625
+ *
3626
+ * GHSA Operations:
3627
+ * - cacheFetch: Cache API responses with TTL
3628
+ * - fetchGhsaDetails: Fetch GitHub Security Advisory details
3629
+ * - getGhsaUrl: Generate GHSA advisory URL
3630
+ * - readCache/writeCache: Persistent cache operations
3631
+ *
3632
+ * Repository Operations:
3633
+ * - GraphQL queries for complex operations
3634
+ * - Integration with Octokit REST API
3635
+ * - Support for GitHub Actions environment variables
3636
+ */
3637
+
3213
3638
  async function readCache(key,
3214
3639
  // 5 minute in milliseconds time to live (TTL).
3215
3640
  ttlMs = 5 * 60 * 1000) {
@@ -3289,11 +3714,8 @@ async function fetchGhsaDetails(ids) {
3289
3714
  }
3290
3715
  }
3291
3716
  } catch (e) {
3292
- const cause = e?.message;
3293
- require$$9.debugFn('error', `Failed to fetch GHSA details${cause ? `: ${cause}` : ''}`);
3294
- require$$9.debugDir('inspect', {
3295
- error: e
3296
- });
3717
+ require$$9.debugFn('error', formatErrorWithDetail('Failed to fetch GHSA details', e));
3718
+ require$$9.debugDir('error', e);
3297
3719
  }
3298
3720
  return results;
3299
3721
  }
@@ -3397,12 +3819,153 @@ async function setGitRemoteGithubRepoUrl(owner, repo, token, cwd = process.cwd()
3397
3819
  await spawn.spawn('git', ['remote', 'set-url', 'origin', url], stdioIgnoreOptions);
3398
3820
  return true;
3399
3821
  } catch (e) {
3400
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
3822
+ require$$9.debugFn('error', `Git command failed: ${quotedCmd}`);
3401
3823
  require$$9.debugDir('inspect', {
3402
- error: e
3824
+ cmd: quotedCmd
3403
3825
  });
3826
+ require$$9.debugDir('error', e);
3827
+ }
3828
+ return false;
3829
+ }
3830
+
3831
+ /**
3832
+ * Command-line utilities for Socket CLI.
3833
+ * Handles argument parsing, flag processing, and command formatting.
3834
+ *
3835
+ * Argument Handling:
3836
+ * - Handles both long (--flag) and short (-f) formats
3837
+ * - Preserves special characters and escaping
3838
+ * - Properly quotes arguments containing spaces
3839
+ *
3840
+ * Command Names:
3841
+ * - commandNameFromCamel: Convert camelCase to kebab-case command names
3842
+ * - commandNameFromKebab: Convert kebab-case to camelCase
3843
+ *
3844
+ * Flag Processing:
3845
+ * - cmdFlagsToString: Format arguments for display with proper escaping
3846
+ * - cmdPrefixMessage: Generate command prefix message
3847
+ * - stripConfigFlags: Remove --config flags from argument list
3848
+ * - stripDebugFlags: Remove debug-related flags
3849
+ * - stripHelpFlags: Remove help flags (-h, --help)
3850
+ */
3851
+
3852
+ const helpFlags = new Set([constants.FLAG_HELP, '-h']);
3853
+
3854
+ /**
3855
+ * Convert command arguments to a properly formatted string representation.
3856
+ */
3857
+ function cmdFlagsToString(args) {
3858
+ const result = [];
3859
+ for (let i = 0, {
3860
+ length
3861
+ } = args; i < length; i += 1) {
3862
+ const arg = args[i].trim();
3863
+ if (arg.startsWith('--')) {
3864
+ const nextArg = i + 1 < length ? args[i + 1].trim() : undefined;
3865
+ // Check if the next item exists and is NOT another flag.
3866
+ if (nextArg && !nextArg.startsWith('--') && !nextArg.startsWith('-')) {
3867
+ result.push(`${arg}=${nextArg}`);
3868
+ i += 1;
3869
+ } else {
3870
+ result.push(arg);
3871
+ }
3872
+ } else {
3873
+ // Include non-flag arguments (commands, package names, etc.).
3874
+ result.push(arg);
3875
+ }
3876
+ }
3877
+ return result.join(' ');
3878
+ }
3879
+
3880
+ /**
3881
+ * Convert flag values to array format for processing.
3882
+ */
3883
+ function cmdFlagValueToArray(value) {
3884
+ if (typeof value === 'string') {
3885
+ return value.trim().split(/, */).filter(Boolean);
3886
+ }
3887
+ if (Array.isArray(value)) {
3888
+ return value.flatMap(cmdFlagValueToArray);
3889
+ }
3890
+ return [];
3891
+ }
3892
+
3893
+ /**
3894
+ * Add command name prefix to message text.
3895
+ */
3896
+ function cmdPrefixMessage(cmdName, text) {
3897
+ const cmdPrefix = cmdName ? `${cmdName}: ` : '';
3898
+ return `${cmdPrefix}${text}`;
3899
+ }
3900
+
3901
+ /**
3902
+ * Filter out Socket flags from argv before passing to subcommands.
3903
+ */
3904
+ function filterFlags(argv, flagsToFilter, exceptions) {
3905
+ const filtered = [];
3906
+
3907
+ // Build set of flags to filter from the provided flag objects.
3908
+ const flagsToFilterSet = new Set();
3909
+ const flagsWithValueSet = new Set();
3910
+ for (const [flagName, flag] of Object.entries(flagsToFilter)) {
3911
+ const longFlag = `--${camelToKebab(flagName)}`;
3912
+ // Special case for negated booleans.
3913
+ if (flagName === 'spinner' || flagName === 'banner') {
3914
+ flagsToFilterSet.add(`--no-${flagName}`);
3915
+ } else {
3916
+ flagsToFilterSet.add(longFlag);
3917
+ }
3918
+ if (flag?.shortFlag) {
3919
+ flagsToFilterSet.add(`-${flag.shortFlag}`);
3920
+ }
3921
+ // Track flags that take values.
3922
+ if (flag.type !== 'boolean') {
3923
+ flagsWithValueSet.add(longFlag);
3924
+ if (flag?.shortFlag) {
3925
+ flagsWithValueSet.add(`-${flag.shortFlag}`);
3926
+ }
3927
+ }
3928
+ }
3929
+ for (let i = 0, {
3930
+ length
3931
+ } = argv; i < length; i += 1) {
3932
+ const arg = argv[i];
3933
+ // Check if this flag should be kept as an exception.
3934
+ if (exceptions?.includes(arg)) {
3935
+ filtered.push(arg);
3936
+ // Handle flags that take values.
3937
+ if (flagsWithValueSet.has(arg)) {
3938
+ // Include the next argument (the flag value).
3939
+ i += 1;
3940
+ if (i < length) {
3941
+ filtered.push(argv[i]);
3942
+ }
3943
+ }
3944
+ } else if (flagsToFilterSet.has(arg)) {
3945
+ // Skip flags that take values.
3946
+ if (flagsWithValueSet.has(arg)) {
3947
+ // Skip the next argument (the flag value).
3948
+ i += 1;
3949
+ }
3950
+ // Skip boolean flags (no additional argument to skip).
3951
+ } else if (arg && Array.from(flagsWithValueSet).some(flag => arg.startsWith(`${flag}=`))) {
3952
+ // Skip --flag=value format for Socket flags unless it's an exception.
3953
+ if (exceptions?.some(exc => arg.startsWith(`${exc}=`))) {
3954
+ filtered.push(arg);
3955
+ }
3956
+ // Otherwise skip it.
3957
+ } else {
3958
+ filtered.push(arg);
3959
+ }
3404
3960
  }
3405
- return false;
3961
+ return filtered;
3962
+ }
3963
+
3964
+ /**
3965
+ * Check if argument is a help flag.
3966
+ */
3967
+ function isHelpFlag(cmdArg) {
3968
+ return helpFlags.has(cmdArg);
3406
3969
  }
3407
3970
 
3408
3971
  /**
@@ -3429,7 +3992,7 @@ async function convertCveToGhsa(cveId) {
3429
3992
  } catch (e) {
3430
3993
  return {
3431
3994
  ok: false,
3432
- message: `Failed to convert CVE to GHSA: ${e instanceof Error ? e.message : 'Unknown error'}`
3995
+ message: `Failed to convert CVE to GHSA: ${getErrorCause(e)}`
3433
3996
  };
3434
3997
  }
3435
3998
  }
@@ -3493,7 +4056,7 @@ async function convertPurlToGhsas(purl) {
3493
4056
  } catch (e) {
3494
4057
  return {
3495
4058
  ok: false,
3496
- message: `Failed to convert PURL to GHSA: ${e instanceof Error ? e.message : constants.UNKNOWN_ERROR}`
4059
+ message: `Failed to convert PURL to GHSA: ${getErrorCause(e)}`
3497
4060
  };
3498
4061
  }
3499
4062
  }
@@ -3564,39 +4127,100 @@ fi
3564
4127
  };
3565
4128
  }
3566
4129
 
3567
- const {
3568
- kInternalsSymbol,
3569
- [kInternalsSymbol]: {
3570
- getSentry
4130
+ /**
4131
+ * Safe wrapper for npm-package-arg that doesn't throw.
4132
+ * Returns undefined if parsing fails.
4133
+ */
4134
+ function safeNpa$1(...args) {
4135
+ try {
4136
+ return Reflect.apply(vendor.npaExports, undefined, args);
4137
+ } catch {}
4138
+ return undefined;
4139
+ }
4140
+
4141
+ function exitWithBinPathError$1(binName) {
4142
+ logger.logger.fail(`Socket unable to locate ${binName}; ensure it is available in the PATH environment variable`);
4143
+ // The exit code 127 indicates that the command or binary being executed
4144
+ // could not be found.
4145
+ // eslint-disable-next-line n/no-process-exit
4146
+ process.exit(127);
4147
+ // This line is never reached in production, but helps tests.
4148
+ throw new Error('process.exit called');
4149
+ }
4150
+ let _npmBinPath;
4151
+ function getNpmBinPath() {
4152
+ if (_npmBinPath === undefined) {
4153
+ _npmBinPath = getNpmBinPathDetails().path;
4154
+ if (!_npmBinPath) {
4155
+ exitWithBinPathError$1(constants.NPM);
4156
+ }
3571
4157
  }
3572
- } = constants.default;
3573
- class AuthError extends Error {}
3574
- class InputError extends Error {
3575
- constructor(message, body) {
3576
- super(message);
3577
- this.body = body;
4158
+ return _npmBinPath;
4159
+ }
4160
+ let _npmBinPathDetails;
4161
+ function getNpmBinPathDetails() {
4162
+ if (_npmBinPathDetails === undefined) {
4163
+ _npmBinPathDetails = findBinPathDetailsSync(constants.NPM);
3578
4164
  }
4165
+ return _npmBinPathDetails;
3579
4166
  }
3580
- async function captureException(exception, hint) {
3581
- const result = captureExceptionSync(exception, hint);
3582
- // "Sleep" for a second, just in case, hopefully enough time to initiate fetch.
3583
- await promises.setTimeout(1000);
3584
- return result;
4167
+ let _npmDirPath;
4168
+ function getNpmDirPath() {
4169
+ if (_npmDirPath === undefined) {
4170
+ const npmBinPath = getNpmBinPath();
4171
+ _npmDirPath = npmBinPath ? findNpmDirPathSync(npmBinPath) : undefined;
4172
+ if (!_npmDirPath) {
4173
+ _npmDirPath = constants.default.ENV.SOCKET_CLI_NPM_PATH || undefined;
4174
+ }
4175
+ if (!_npmDirPath) {
4176
+ let message = 'Unable to find npm CLI install directory.';
4177
+ if (npmBinPath) {
4178
+ message += `\nSearched parent directories of ${path.dirname(npmBinPath)}.`;
4179
+ }
4180
+ message += '\n\nThis is may be a bug with socket-npm related to changes to the npm CLI.';
4181
+ message += `\nPlease report to ${constants.default.SOCKET_CLI_ISSUES_URL}.`;
4182
+ logger.logger.fail(message);
4183
+ // The exit code 127 indicates that the command or binary being executed
4184
+ // could not be found.
4185
+ // eslint-disable-next-line n/no-process-exit
4186
+ process.exit(127);
4187
+ // This line is never reached in production, but helps tests.
4188
+ throw new Error('process.exit called');
4189
+ }
4190
+ }
4191
+ return _npmDirPath;
3585
4192
  }
3586
- function captureExceptionSync(exception, hint) {
3587
- const Sentry = getSentry();
3588
- if (!Sentry) {
3589
- return '';
4193
+ let _npmRequire;
4194
+ function getNpmRequire() {
4195
+ if (_npmRequire === undefined) {
4196
+ const npmDirPath = getNpmDirPath();
4197
+ const npmNmPath = path.join(npmDirPath, `${constants.NODE_MODULES}/npm`);
4198
+ _npmRequire = require$$5.createRequire(path.join(fs$1.existsSync(npmNmPath) ? npmNmPath : npmDirPath, '<dummy-basename>'));
3590
4199
  }
3591
- require$$9.debugFn('notice', 'send: exception to Sentry');
3592
- return Sentry.captureException(exception, hint);
4200
+ return _npmRequire;
3593
4201
  }
3594
-
3595
- function npa(...args) {
3596
- try {
3597
- return Reflect.apply(vendor.npaExports, undefined, args);
3598
- } catch {}
3599
- return undefined;
4202
+ let _npxBinPath;
4203
+ function getNpxBinPath() {
4204
+ if (_npxBinPath === undefined) {
4205
+ _npxBinPath = getNpxBinPathDetails().path;
4206
+ if (!_npxBinPath) {
4207
+ exitWithBinPathError$1('npx');
4208
+ }
4209
+ }
4210
+ return _npxBinPath;
4211
+ }
4212
+ let _npxBinPathDetails;
4213
+ function getNpxBinPathDetails() {
4214
+ if (_npxBinPathDetails === undefined) {
4215
+ _npxBinPathDetails = findBinPathDetailsSync('npx');
4216
+ }
4217
+ return _npxBinPathDetails;
4218
+ }
4219
+ function isNpmBinPathShadowed() {
4220
+ return getNpmBinPathDetails().shadowed;
4221
+ }
4222
+ function isNpxBinPathShadowed() {
4223
+ return getNpxBinPathDetails().shadowed;
3600
4224
  }
3601
4225
 
3602
4226
  function shadowNpmInstall(options) {
@@ -3662,6 +4286,24 @@ function shadowNpmInstall(options) {
3662
4286
  return spawnPromise;
3663
4287
  }
3664
4288
 
4289
+ /**
4290
+ * Package manager agent utilities for Socket CLI.
4291
+ * Manages package installation via different package managers.
4292
+ *
4293
+ * Key Functions:
4294
+ * - runAgentInstall: Execute package installation with detected agent
4295
+ *
4296
+ * Supported Agents:
4297
+ * - npm: Node Package Manager
4298
+ * - pnpm: Fast, disk space efficient package manager
4299
+ * - yarn: Alternative package manager
4300
+ *
4301
+ * Features:
4302
+ * - Automatic agent detection
4303
+ * - Shadow installation for security scanning
4304
+ * - Spinner support for progress indication
4305
+ */
4306
+
3665
4307
  function runAgentInstall(pkgEnvDetails, options) {
3666
4308
  const {
3667
4309
  agent,
@@ -3693,6 +4335,9 @@ function runAgentInstall(pkgEnvDetails, options) {
3693
4335
  const installArgs = isPnpm && isCi ? ['install', '--no-frozen-lockfile', ...args] : ['install', ...args];
3694
4336
  return spawn.spawn(agentExecPath, installArgs, {
3695
4337
  cwd: pkgPath,
4338
+ // On Windows, package managers are often .cmd files that require shell execution.
4339
+ // The spawn function from @socketsecurity/registry will handle this properly
4340
+ // when shell is true.
3696
4341
  shell: constants.default.WIN32,
3697
4342
  spinner,
3698
4343
  stdio: 'inherit',
@@ -3706,6 +4351,32 @@ function runAgentInstall(pkgEnvDetails, options) {
3706
4351
  });
3707
4352
  }
3708
4353
 
4354
+ /**
4355
+ * Package environment detection utilities for Socket CLI.
4356
+ * Analyzes project environment and package manager configuration.
4357
+ *
4358
+ * Key Functions:
4359
+ * - getPackageEnvironment: Detect package manager and project details
4360
+ * - makeConcurrentExecLimit: Calculate concurrent execution limits
4361
+ *
4362
+ * Environment Detection:
4363
+ * - Detects npm, pnpm, yarn, bun package managers
4364
+ * - Analyzes lockfiles for version information
4365
+ * - Determines Node.js and engine requirements
4366
+ * - Identifies workspace configurations
4367
+ *
4368
+ * Features:
4369
+ * - Browser target detection via browserslist
4370
+ * - Engine compatibility checking
4371
+ * - Package manager version detection
4372
+ * - Workspace and monorepo support
4373
+ *
4374
+ * Usage:
4375
+ * - Auto-detecting appropriate package manager
4376
+ * - Validating environment compatibility
4377
+ * - Configuring concurrent execution limits
4378
+ */
4379
+
3709
4380
  const {
3710
4381
  BUN,
3711
4382
  BUN_LOCK,
@@ -3755,6 +4426,9 @@ const readLockFileByAgent = (() => {
3755
4426
  // https://bun.sh/guides/install/yarnlock
3756
4427
  return (await spawn.spawn(agentExecPath, [lockPath], {
3757
4428
  cwd,
4429
+ // On Windows, bun is often a .cmd file that requires shell execution.
4430
+ // The spawn function from @socketsecurity/registry will handle this properly
4431
+ // when shell is true.
3758
4432
  shell: constants.default.WIN32
3759
4433
  })).stdout;
3760
4434
  }
@@ -3775,7 +4449,7 @@ const LOCKS = {
3775
4449
  [constants.PNPM_LOCK_YAML]: PNPM,
3776
4450
  [constants.YARN_LOCK]: YARN_CLASSIC,
3777
4451
  [VLT_LOCK_JSON]: VLT,
3778
- // Lastly, look for a hidden lock file which is present if .npmrc has package-lock=false:
4452
+ // Lastly, look for a hidden lockfile which is present if .npmrc has package-lock=false:
3779
4453
  // https://docs.npmjs.com/cli/v10/configuring-npm/package-lock-json#hidden-lockfiles
3780
4454
  //
3781
4455
  // Unlike the other LOCKS keys this key contains a directory AND filename so
@@ -3830,13 +4504,17 @@ async function getAgentVersion(agent, agentExecPath, cwd) {
3830
4504
  // All package managers support the "--version" flag.
3831
4505
  (await spawn.spawn(agentExecPath, [constants.FLAG_VERSION], {
3832
4506
  cwd,
4507
+ // On Windows, package managers are often .cmd files that require shell execution.
4508
+ // The spawn function from @socketsecurity/registry will handle this properly
4509
+ // when shell is true.
3833
4510
  shell: constants.default.WIN32
3834
4511
  })).stdout) ?? undefined;
3835
4512
  } catch (e) {
3836
- require$$9.debugFn('error', `caught: ${quotedCmd} failed`);
4513
+ require$$9.debugFn('error', `Package manager command failed: ${quotedCmd}`);
3837
4514
  require$$9.debugDir('inspect', {
3838
- error: e
4515
+ cmd: quotedCmd
3839
4516
  });
4517
+ require$$9.debugDir('error', e);
3840
4518
  }
3841
4519
  return result;
3842
4520
  }
@@ -4026,7 +4704,7 @@ async function detectAndValidatePackageEnvironment(cwd, options) {
4026
4704
  cause: cmdPrefixMessage(cmdName, `Package engine "node" requires ${pkgRequirements.node}. Current version: ${nodeVersion}`)
4027
4705
  };
4028
4706
  }
4029
- const lockName = details.lockName ?? 'lock file';
4707
+ const lockName = details.lockName ?? 'lockfile';
4030
4708
  if (details.lockName === undefined || details.lockSrc === undefined) {
4031
4709
  return {
4032
4710
  ok: false,
@@ -4065,39 +4743,47 @@ async function detectAndValidatePackageEnvironment(cwd, options) {
4065
4743
  };
4066
4744
  }
4067
4745
 
4746
+ /**
4747
+ * Ecosystem type utilities for Socket CLI.
4748
+ * Manages package ecosystem identifiers and mappings.
4749
+ *
4750
+ * Constants:
4751
+ * - ALL_ECOSYSTEMS: Complete list of supported ecosystems
4752
+ * - ECOSYSTEM_MAP: Map ecosystem strings to PURL types
4753
+ *
4754
+ * Type Definitions:
4755
+ * - PURL_Type: Package URL type from Socket SDK
4756
+ *
4757
+ * Supported Ecosystems:
4758
+ * - apk, bitbucket, cargo, chrome, cocoapods, composer
4759
+ * - conan, conda, cran, deb, docker, gem, generic
4760
+ * - github, gitlab, go, hackage, hex, huggingface
4761
+ * - maven, mlflow, npm, nuget, oci, pub, pypi, rpm, swift
4762
+ *
4763
+ * Usage:
4764
+ * - Validates ecosystem types
4765
+ * - Maps between different ecosystem representations
4766
+ * - Ensures type safety for ecosystem operations
4767
+ */
4768
+
4068
4769
  const ALL_ECOSYSTEMS = ['apk', 'bitbucket', 'cargo', 'chrome', 'cocoapods', 'composer', 'conan', 'conda', 'cran', 'deb', 'docker', 'gem', 'generic', 'github', 'golang', 'hackage', 'hex', 'huggingface', 'maven', 'mlflow', constants.NPM, 'nuget', 'oci', 'pub', 'pypi', 'qpkg', 'rpm', 'swift', 'swid', 'unknown'];
4069
4770
  new Set(ALL_ECOSYSTEMS);
4070
4771
  function getEcosystemChoicesForMeow() {
4071
4772
  return [...ALL_ECOSYSTEMS];
4072
4773
  }
4073
4774
 
4074
- function exitWithBinPathError(binName) {
4075
- logger.logger.fail(`Socket unable to locate ${binName}; ensure it is available in the PATH environment variable`);
4076
- // The exit code 127 indicates that the command or binary being executed
4077
- // could not be found.
4078
- // eslint-disable-next-line n/no-process-exit
4079
- process.exit(127);
4080
- }
4081
- let _pnpmBinPath;
4082
- function getPnpmBinPath() {
4083
- if (_pnpmBinPath === undefined) {
4084
- _pnpmBinPath = getPnpmBinPathDetails().path;
4085
- if (!_pnpmBinPath) {
4086
- exitWithBinPathError('pnpm');
4087
- }
4088
- }
4089
- return _pnpmBinPath;
4090
- }
4091
- let _pnpmBinPathDetails;
4092
- function getPnpmBinPathDetails() {
4093
- if (_pnpmBinPathDetails === undefined) {
4094
- _pnpmBinPathDetails = findBinPathDetailsSync('pnpm');
4095
- }
4096
- return _pnpmBinPathDetails;
4097
- }
4098
- function isPnpmBinPathShadowed() {
4099
- return getPnpmBinPathDetails().shadowed;
4100
- }
4775
+ /**
4776
+ * Filter configuration utilities for Socket CLI.
4777
+ * Manages filter configuration normalization for security scanning.
4778
+ *
4779
+ * Key Functions:
4780
+ * - toFilterConfig: Normalize filter configuration objects
4781
+ *
4782
+ * Usage:
4783
+ * - Normalizes user-provided filter objects
4784
+ * - Ensures proper structure for filter configuration
4785
+ * - Validates boolean and array values
4786
+ */
4101
4787
 
4102
4788
  function toFilterConfig(obj) {
4103
4789
  const normalized = {
@@ -4197,6 +4883,30 @@ const ALERT_SEVERITY = createEnum({
4197
4883
  low: 'low'
4198
4884
  });
4199
4885
 
4886
+ /**
4887
+ * Color and markdown formatting utilities for Socket CLI.
4888
+ * Provides dual-mode formatting for terminal colors or markdown output.
4889
+ *
4890
+ * Key Class:
4891
+ * - ColorOrMarkdown: Dual-mode formatter for terminal/markdown output
4892
+ *
4893
+ * Formatting Methods:
4894
+ * - bold: Bold text formatting
4895
+ * - codeBlock: Code block formatting
4896
+ * - codeInline: Inline code formatting
4897
+ * - header: Section headers
4898
+ * - hyperlink: Clickable links
4899
+ * - indent: Text indentation
4900
+ * - italic: Italic text formatting
4901
+ * - list: Bullet list formatting
4902
+ * - table: Table formatting
4903
+ *
4904
+ * Usage:
4905
+ * - Switches between terminal colors and markdown based on output format
4906
+ * - Supports both interactive terminal and report generation
4907
+ * - Handles hyperlink fallbacks for terminals without link support
4908
+ */
4909
+
4200
4910
  class ColorOrMarkdown {
4201
4911
  constructor(useMarkdown) {
4202
4912
  this.useMarkdown = !!useMarkdown;
@@ -4242,6 +4952,28 @@ function getTranslations() {
4242
4952
  return _translations;
4243
4953
  }
4244
4954
 
4955
+ /**
4956
+ * Socket package alert utilities for Socket CLI.
4957
+ * Handles security alerts, vulnerabilities, and package risk assessment.
4958
+ *
4959
+ * Key Functions:
4960
+ * - addArtifactToAlertsMap: Add security alert to package map
4961
+ * - logAlertsMap: Display alerts in formatted output
4962
+ * - shouldSkipPackageAlert: Filter alerts based on criteria
4963
+ *
4964
+ * Alert Types:
4965
+ * - CVE: Common Vulnerabilities and Exposures
4966
+ * - GHSA: GitHub Security Advisories
4967
+ * - Package quality issues
4968
+ * - Supply chain risks
4969
+ *
4970
+ * Features:
4971
+ * - Alert severity classification (critical/high/medium/low)
4972
+ * - Fix type detection (major/minor/patch/none)
4973
+ * - Alert filtering and suppression
4974
+ * - Colorized terminal output
4975
+ */
4976
+
4245
4977
  const ALERT_SEVERITY_COLOR = createEnum({
4246
4978
  critical: 'magenta',
4247
4979
  high: 'red',
@@ -4586,6 +5318,26 @@ function logAlertsMap(alertsMap, options) {
4586
5318
  output.write('\n');
4587
5319
  }
4588
5320
 
5321
+ /**
5322
+ * Alerts map utilities for Socket CLI.
5323
+ * Manages security alerts and vulnerability mappings for packages.
5324
+ *
5325
+ * Key Functions:
5326
+ * - getAlertsMapFromPnpmLockfile: Extract alerts from pnpm lockfile
5327
+ * - getAlertsMapFromPurls: Get alerts for specific package URLs
5328
+ * - processAlertsApiResponse: Process API response into alerts map
5329
+ *
5330
+ * Alert Processing:
5331
+ * - Filters alerts based on socket.yml configuration
5332
+ * - Maps package URLs to security vulnerabilities
5333
+ * - Supports batch processing for performance
5334
+ *
5335
+ * Integration:
5336
+ * - Works with pnpm lockfiles for dependency scanning
5337
+ * - Uses Socket API for vulnerability data
5338
+ * - Respects filter configurations from socket.yml
5339
+ */
5340
+
4589
5341
  async function getAlertsMapFromPnpmLockfile(lockfile, options) {
4590
5342
  const purls = await extractPurlsFromPnpmLockfile(lockfile);
4591
5343
  return await getAlertsMapFromPurls(purls, {
@@ -4686,6 +5438,183 @@ async function getAlertsMapFromPurls(purls, options) {
4686
5438
  return alertsByPurl;
4687
5439
  }
4688
5440
 
5441
+ /**
5442
+ * npm package specification utilities for Socket CLI.
5443
+ * Parses and handles various npm package specification formats.
5444
+ *
5445
+ * Supported Formats:
5446
+ * - Regular packages: lodash, lodash@4.17.21
5447
+ * - Scoped packages: @types/node, @types/node@20.0.0
5448
+ * - Version ranges: lodash@^4.0.0, lodash@~4.17.0
5449
+ * - Git URLs: git+https://github.com/user/repo.git
5450
+ * - File paths: file:../local-package
5451
+ * - Aliases: my-alias@npm:real-package@1.0.0
5452
+ *
5453
+ * Key Functions:
5454
+ * - safeNpa: Safe wrapper for npm-package-arg
5455
+ * - safeNpmSpecToPurl: Convert npm spec to PURL
5456
+ * - safeParseNpmSpec: Parse npm spec to name/version
5457
+ *
5458
+ * Error Handling:
5459
+ * - Returns undefined for invalid specs
5460
+ * - Fallback parsing for edge cases
5461
+ * - Safe against malformed input
5462
+ */
5463
+
5464
+
5465
+ // @ts-expect-error - Result is re-exported below.
5466
+
5467
+ /**
5468
+ * Safe wrapper for npm-package-arg that doesn't throw.
5469
+ * Returns undefined if parsing fails.
5470
+ */
5471
+ function safeNpa(...args) {
5472
+ try {
5473
+ return Reflect.apply(vendor.npaExports, undefined, args);
5474
+ } catch {}
5475
+ return undefined;
5476
+ }
5477
+
5478
+ /**
5479
+ * Parse npm package specification into name and version.
5480
+ * Uses npm-package-arg for proper handling of various spec formats:
5481
+ * - Regular packages: lodash, lodash@4.17.21
5482
+ * - Scoped packages: @types/node, @types/node@20.0.0
5483
+ * - Version ranges: lodash@^4.0.0
5484
+ * - Git URLs, file paths, etc.
5485
+ *
5486
+ * Returns undefined if parsing fails.
5487
+ */
5488
+ function safeParseNpmSpec(pkgSpec) {
5489
+ // Use npm-package-arg for proper spec parsing.
5490
+ const parsed = safeNpa(pkgSpec);
5491
+ if (!parsed) {
5492
+ // Fallback to simple parsing if npm-package-arg fails.
5493
+ // Handle scoped packages first to avoid confusion with version delimiter.
5494
+ if (pkgSpec.startsWith('@')) {
5495
+ const scopedMatch = pkgSpec.match(/^(@[^/@]+\/[^/@]+)(?:@(.+))?$/);
5496
+ if (scopedMatch) {
5497
+ return {
5498
+ name: scopedMatch[1],
5499
+ version: scopedMatch[2]
5500
+ };
5501
+ }
5502
+ }
5503
+
5504
+ // Handle regular packages.
5505
+ const atIndex = pkgSpec.indexOf('@');
5506
+ if (atIndex === -1) {
5507
+ return {
5508
+ name: pkgSpec,
5509
+ version: undefined
5510
+ };
5511
+ }
5512
+ return {
5513
+ name: pkgSpec.slice(0, atIndex),
5514
+ version: pkgSpec.slice(atIndex + 1)
5515
+ };
5516
+ }
5517
+
5518
+ // Extract name and version from parsed spec.
5519
+ const name = parsed.name || pkgSpec;
5520
+ let version;
5521
+
5522
+ // Handle different spec types from npm-package-arg.
5523
+ if (parsed.type === 'tag' || parsed.type === 'version' || parsed.type === 'range') {
5524
+ // For npm registry packages:
5525
+ // - type 'tag': latest, beta, etc.
5526
+ // - type 'version': exact version like 1.0.0
5527
+ // - type 'range': version range like ^1.0.0, ~1.0.0, or * for bare names
5528
+ // Don't include '*' as a version - it means "any version".
5529
+ if (parsed.fetchSpec && parsed.fetchSpec !== '*') {
5530
+ version = parsed.fetchSpec;
5531
+ } else if (parsed.rawSpec && parsed.rawSpec !== '*' && parsed.rawSpec !== parsed.name) {
5532
+ version = parsed.rawSpec;
5533
+ }
5534
+ } else if (parsed.type === 'git' || parsed.type === 'remote' || parsed.type === 'file') {
5535
+ // For non-registry specs, use rawSpec if different from name.
5536
+ if (parsed.rawSpec && parsed.rawSpec !== parsed.name) {
5537
+ version = parsed.rawSpec;
5538
+ }
5539
+ }
5540
+ return {
5541
+ name,
5542
+ version
5543
+ };
5544
+ }
5545
+
5546
+ /**
5547
+ * Convert npm package spec to PURL string.
5548
+ * Handles various npm spec formats and converts them to standardized PURLs.
5549
+ * Returns undefined if conversion fails.
5550
+ */
5551
+ function safeNpmSpecToPurl(pkgSpec) {
5552
+ const parsed = safeParseNpmSpec(pkgSpec);
5553
+ if (!parsed) {
5554
+ return undefined;
5555
+ }
5556
+ const {
5557
+ name,
5558
+ version
5559
+ } = parsed;
5560
+
5561
+ // Create PURL object to ensure proper formatting.
5562
+ const purlObj = createPurlObject({
5563
+ type: constants.NPM,
5564
+ name,
5565
+ version,
5566
+ throws: false
5567
+ });
5568
+ return purlObj?.toString() ?? `pkg:${constants.NPM}/${name}${version ? `@${version}` : ''}`;
5569
+ }
5570
+
5571
+ /**
5572
+ * PNPM path resolution utilities for Socket CLI.
5573
+ * Locates and caches PNPM binary paths.
5574
+ *
5575
+ * Key Functions:
5576
+ * - getPnpmBinPath: Get cached PNPM binary path
5577
+ * - getPnpmBinPathDetails: Get detailed PNPM path information
5578
+ *
5579
+ * Error Handling:
5580
+ * - Exits with code 127 if PNPM not found
5581
+ * - Provides clear error messages for missing binaries
5582
+ *
5583
+ * Caching:
5584
+ * - Caches binary path lookups for performance
5585
+ * - Prevents repeated PATH searches
5586
+ */
5587
+
5588
+ function exitWithBinPathError(binName) {
5589
+ logger.logger.fail(`Socket unable to locate ${binName}; ensure it is available in the PATH environment variable`);
5590
+ // The exit code 127 indicates that the command or binary being executed
5591
+ // could not be found.
5592
+ // eslint-disable-next-line n/no-process-exit
5593
+ process.exit(127);
5594
+ // This line is never reached in production, but helps tests.
5595
+ throw new Error('process.exit called');
5596
+ }
5597
+ let _pnpmBinPath;
5598
+ function getPnpmBinPath() {
5599
+ if (_pnpmBinPath === undefined) {
5600
+ _pnpmBinPath = getPnpmBinPathDetails().path;
5601
+ if (!_pnpmBinPath) {
5602
+ exitWithBinPathError('pnpm');
5603
+ }
5604
+ }
5605
+ return _pnpmBinPath;
5606
+ }
5607
+ let _pnpmBinPathDetails;
5608
+ function getPnpmBinPathDetails() {
5609
+ if (_pnpmBinPathDetails === undefined) {
5610
+ _pnpmBinPathDetails = findBinPathDetailsSync('pnpm');
5611
+ }
5612
+ return _pnpmBinPathDetails;
5613
+ }
5614
+ function isPnpmBinPathShadowed() {
5615
+ return getPnpmBinPathDetails().shadowed;
5616
+ }
5617
+
4689
5618
  exports.AuthError = AuthError;
4690
5619
  exports.COMPLETION_CMD_PREFIX = COMPLETION_CMD_PREFIX;
4691
5620
  exports.InputError = InputError;
@@ -4699,6 +5628,8 @@ exports.cmdPrefixMessage = cmdPrefixMessage;
4699
5628
  exports.convertCveToGhsa = convertCveToGhsa;
4700
5629
  exports.convertPurlToGhsas = convertPurlToGhsas;
4701
5630
  exports.createEnum = createEnum;
5631
+ exports.debugFileOp = debugFileOp;
5632
+ exports.debugScan = debugScan;
4702
5633
  exports.detectAndValidatePackageEnvironment = detectAndValidatePackageEnvironment;
4703
5634
  exports.detectDefaultBranch = detectDefaultBranch;
4704
5635
  exports.determineOrgSlug = determineOrgSlug;
@@ -4707,8 +5638,10 @@ exports.extractTier1ReachabilityScanId = extractTier1ReachabilityScanId;
4707
5638
  exports.failMsgWithBadge = failMsgWithBadge;
4708
5639
  exports.fetchGhsaDetails = fetchGhsaDetails;
4709
5640
  exports.fetchOrganization = fetchOrganization;
5641
+ exports.fileLink = fileLink;
4710
5642
  exports.filterFlags = filterFlags;
4711
5643
  exports.findUp = findUp;
5644
+ exports.formatErrorWithDetail = formatErrorWithDetail;
4712
5645
  exports.getAlertsMapFromPnpmLockfile = getAlertsMapFromPnpmLockfile;
4713
5646
  exports.getAlertsMapFromPurls = getAlertsMapFromPurls;
4714
5647
  exports.getBaseBranch = getBaseBranch;
@@ -4718,6 +5651,7 @@ exports.getConfigValueOrUndef = getConfigValueOrUndef;
4718
5651
  exports.getDefaultOrgSlug = getDefaultOrgSlug;
4719
5652
  exports.getEcosystemChoicesForMeow = getEcosystemChoicesForMeow;
4720
5653
  exports.getEnterpriseOrgs = getEnterpriseOrgs;
5654
+ exports.getErrorCause = getErrorCause;
4721
5655
  exports.getFlagApiRequirementsOutput = getFlagApiRequirementsOutput;
4722
5656
  exports.getFlagListOutput = getFlagListOutput;
4723
5657
  exports.getMajor = getMajor;
@@ -4765,6 +5699,7 @@ exports.isSupportedConfigKey = isSupportedConfigKey;
4765
5699
  exports.isYarnBerry = isYarnBerry;
4766
5700
  exports.isYarnBinPathShadowed = isYarnBinPathShadowed;
4767
5701
  exports.logAlertsMap = logAlertsMap;
5702
+ exports.mailtoLink = mailtoLink;
4768
5703
  exports.mapToObject = mapToObject;
4769
5704
  exports.mdTable = mdTable;
4770
5705
  exports.mdTableOfPairs = mdTableOfPairs;
@@ -4773,7 +5708,6 @@ exports.meowOrExit = meowOrExit;
4773
5708
  exports.meowWithSubcommands = meowWithSubcommands;
4774
5709
  exports.msAtHome = msAtHome;
4775
5710
  exports.normalizePurl = normalizePurl;
4776
- exports.npa = npa;
4777
5711
  exports.parsePnpmLockfile = parsePnpmLockfile;
4778
5712
  exports.queryApiSafeJson = queryApiSafeJson;
4779
5713
  exports.queryApiSafeText = queryApiSafeText;
@@ -4782,10 +5716,15 @@ exports.readOrDefaultSocketJsonUp = readOrDefaultSocketJsonUp;
4782
5716
  exports.readPnpmLockfile = readPnpmLockfile;
4783
5717
  exports.readSocketJsonSync = readSocketJsonSync;
4784
5718
  exports.runAgentInstall = runAgentInstall;
5719
+ exports.safeNpa = safeNpa$1;
5720
+ exports.safeNpmSpecToPurl = safeNpmSpecToPurl;
4785
5721
  exports.sendApiRequest = sendApiRequest;
4786
5722
  exports.serializeResultJson = serializeResultJson;
4787
5723
  exports.setGitRemoteGithubRepoUrl = setGitRemoteGithubRepoUrl;
4788
5724
  exports.setupSdk = setupSdk;
5725
+ exports.socketDashboardLink = socketDashboardLink;
5726
+ exports.socketDocsLink = socketDocsLink;
5727
+ exports.socketPackageLink = socketPackageLink;
4789
5728
  exports.spawnCdxgenDlx = spawnCdxgenDlx;
4790
5729
  exports.spawnCoanaDlx = spawnCoanaDlx;
4791
5730
  exports.spawnSynpDlx = spawnSynpDlx;
@@ -4794,6 +5733,7 @@ exports.tildify = tildify;
4794
5733
  exports.toFilterConfig = toFilterConfig;
4795
5734
  exports.updateConfigValue = updateConfigValue;
4796
5735
  exports.walkNestedMap = walkNestedMap;
5736
+ exports.webLink = webLink;
4797
5737
  exports.writeSocketJson = writeSocketJson;
4798
- //# debugId=4f982f8d-ea52-46a2-a41c-84d9eac292ab
5738
+ //# debugId=ea20d1df-782c-49c5-bbda-ab4eac27ce58
4799
5739
  //# sourceMappingURL=utils.js.map