@vibe-validate/cli 0.17.6-rc.2 → 0.18.0-rc.1

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 (89) hide show
  1. package/dist/bin/vibe-validate +4 -0
  2. package/dist/bin/vibe-validate.js +4 -0
  3. package/dist/bin/vibe-validate.js.map +1 -1
  4. package/dist/bin/vv +4 -0
  5. package/dist/commands/cleanup.d.ts.map +1 -1
  6. package/dist/commands/cleanup.js +5 -2
  7. package/dist/commands/cleanup.js.map +1 -1
  8. package/dist/commands/config.d.ts.map +1 -1
  9. package/dist/commands/config.js +3 -1
  10. package/dist/commands/config.js.map +1 -1
  11. package/dist/commands/create-extractor.d.ts.map +1 -1
  12. package/dist/commands/create-extractor.js +3 -1
  13. package/dist/commands/create-extractor.js.map +1 -1
  14. package/dist/commands/doctor.d.ts.map +1 -1
  15. package/dist/commands/doctor.js +11 -5
  16. package/dist/commands/doctor.js.map +1 -1
  17. package/dist/commands/generate-workflow.d.ts.map +1 -1
  18. package/dist/commands/generate-workflow.js +6 -2
  19. package/dist/commands/generate-workflow.js.map +1 -1
  20. package/dist/commands/history.d.ts.map +1 -1
  21. package/dist/commands/history.js +23 -13
  22. package/dist/commands/history.js.map +1 -1
  23. package/dist/commands/init.d.ts.map +1 -1
  24. package/dist/commands/init.js +3 -1
  25. package/dist/commands/init.js.map +1 -1
  26. package/dist/commands/pre-commit.d.ts.map +1 -1
  27. package/dist/commands/pre-commit.js +5 -2
  28. package/dist/commands/pre-commit.js.map +1 -1
  29. package/dist/commands/run.d.ts.map +1 -1
  30. package/dist/commands/run.js +12 -10
  31. package/dist/commands/run.js.map +1 -1
  32. package/dist/commands/state.d.ts.map +1 -1
  33. package/dist/commands/state.js +15 -10
  34. package/dist/commands/state.js.map +1 -1
  35. package/dist/commands/sync-check.js +5 -5
  36. package/dist/commands/sync-check.js.map +1 -1
  37. package/dist/commands/watch-pr.d.ts +16 -0
  38. package/dist/commands/watch-pr.d.ts.map +1 -1
  39. package/dist/commands/watch-pr.js +572 -318
  40. package/dist/commands/watch-pr.js.map +1 -1
  41. package/dist/schemas/watch-pr-result.schema.d.ts +2010 -0
  42. package/dist/schemas/watch-pr-result.schema.d.ts.map +1 -0
  43. package/dist/schemas/watch-pr-result.schema.js +335 -0
  44. package/dist/schemas/watch-pr-result.schema.js.map +1 -0
  45. package/dist/schemas/watch-pr-schema.d.ts +6 -6
  46. package/dist/services/cache-manager.d.ts +113 -0
  47. package/dist/services/cache-manager.d.ts.map +1 -0
  48. package/dist/services/cache-manager.js +211 -0
  49. package/dist/services/cache-manager.js.map +1 -0
  50. package/dist/services/ci-providers/github-actions.d.ts.map +1 -1
  51. package/dist/services/ci-providers/github-actions.js +10 -16
  52. package/dist/services/ci-providers/github-actions.js.map +1 -1
  53. package/dist/services/external-check-extractor.d.ts +66 -0
  54. package/dist/services/external-check-extractor.d.ts.map +1 -0
  55. package/dist/services/external-check-extractor.js +114 -0
  56. package/dist/services/external-check-extractor.js.map +1 -0
  57. package/dist/services/extraction-mode-detector.d.ts +85 -0
  58. package/dist/services/extraction-mode-detector.d.ts.map +1 -0
  59. package/dist/services/extraction-mode-detector.js +200 -0
  60. package/dist/services/extraction-mode-detector.js.map +1 -0
  61. package/dist/services/github-fetcher.d.ts +210 -0
  62. package/dist/services/github-fetcher.d.ts.map +1 -0
  63. package/dist/services/github-fetcher.js +412 -0
  64. package/dist/services/github-fetcher.js.map +1 -0
  65. package/dist/services/history-summary-builder.d.ts +74 -0
  66. package/dist/services/history-summary-builder.d.ts.map +1 -0
  67. package/dist/services/history-summary-builder.js +199 -0
  68. package/dist/services/history-summary-builder.js.map +1 -0
  69. package/dist/services/watch-pr-orchestrator.d.ts +119 -0
  70. package/dist/services/watch-pr-orchestrator.d.ts.map +1 -0
  71. package/dist/services/watch-pr-orchestrator.js +420 -0
  72. package/dist/services/watch-pr-orchestrator.js.map +1 -0
  73. package/dist/utils/command-name.d.ts +21 -0
  74. package/dist/utils/command-name.d.ts.map +1 -0
  75. package/dist/utils/command-name.js +45 -0
  76. package/dist/utils/command-name.js.map +1 -0
  77. package/dist/utils/pid-lock.d.ts.map +1 -1
  78. package/dist/utils/pid-lock.js +3 -3
  79. package/dist/utils/pid-lock.js.map +1 -1
  80. package/dist/utils/secret-scanning.d.ts +1 -1
  81. package/dist/utils/secret-scanning.d.ts.map +1 -1
  82. package/dist/utils/secret-scanning.js +32 -4
  83. package/dist/utils/secret-scanning.js.map +1 -1
  84. package/dist/utils/temp-files.d.ts.map +1 -1
  85. package/dist/utils/temp-files.js +2 -2
  86. package/dist/utils/temp-files.js.map +1 -1
  87. package/dist/utils/validate-workflow.js +7 -7
  88. package/dist/utils/validate-workflow.js.map +1 -1
  89. package/package.json +7 -7
@@ -0,0 +1,420 @@
1
+ /**
2
+ * WatchPROrchestrator - Coordinate all components to build complete WatchPRResult
3
+ *
4
+ * Responsibilities:
5
+ * - Coordinate data fetching (PR metadata, checks, history, changes)
6
+ * - Extract errors from check logs (matrix + non-matrix modes)
7
+ * - Extract external check details (codecov, SonarCloud, etc.)
8
+ * - Build complete WatchPRResult with validation
9
+ * - Generate intelligent guidance
10
+ * - Handle caching (save/retrieve results)
11
+ * - Select output format (YAML on failure, text on success)
12
+ *
13
+ * @packageDocumentation
14
+ */
15
+ import { CacheManager } from './cache-manager.js';
16
+ import { CodecovExtractor, ExternalExtractorRegistry, SonarCloudExtractor, } from './external-check-extractor.js';
17
+ import { ExtractionModeDetector } from './extraction-mode-detector.js';
18
+ import { GitHubFetcher } from './github-fetcher.js';
19
+ import { HistorySummaryBuilder } from './history-summary-builder.js';
20
+ /**
21
+ * WatchPROrchestrator - Build complete WatchPRResult
22
+ */
23
+ export class WatchPROrchestrator {
24
+ owner;
25
+ repo;
26
+ fetcher;
27
+ historyBuilder;
28
+ extractionDetector;
29
+ externalCheckExtractor;
30
+ cacheManager;
31
+ constructor(owner, repo) {
32
+ this.owner = owner;
33
+ this.repo = repo;
34
+ this.fetcher = new GitHubFetcher(owner, repo);
35
+ this.historyBuilder = new HistorySummaryBuilder(owner, repo);
36
+ this.extractionDetector = new ExtractionModeDetector();
37
+ // Initialize external check extractor registry
38
+ this.externalCheckExtractor = new ExternalExtractorRegistry();
39
+ this.externalCheckExtractor.register(new CodecovExtractor());
40
+ this.externalCheckExtractor.register(new SonarCloudExtractor());
41
+ }
42
+ /**
43
+ * Build complete WatchPRResult
44
+ *
45
+ * @param prNumber - PR number
46
+ * @param options - Options (useCache, forceFetch)
47
+ * @returns Complete WatchPRResult
48
+ */
49
+ // eslint-disable-next-line sonarjs/cognitive-complexity
50
+ async buildResult(prNumber, options = {}) {
51
+ const { useCache = true } = options;
52
+ // Initialize cache manager if caching enabled (for logs only)
53
+ if (useCache && !this.cacheManager) {
54
+ this.cacheManager = new CacheManager(`${this.owner}/${this.repo}`, prNumber);
55
+ }
56
+ // Always fetch fresh PR metadata and checks from GitHub
57
+ // Cache is ONLY used for expensive log downloads, NOT for status
58
+ const prMetadata = await this.fetcher.fetchPRDetails(prNumber);
59
+ // Fetch checks
60
+ const checks = await this.fetcher.fetchChecks(prNumber);
61
+ // Classify checks into GitHub Actions vs external
62
+ const githubActions = [];
63
+ const rawExternalChecks = [];
64
+ for (const check of checks) {
65
+ if (check.type === 'github_action') {
66
+ // GitHub Action check - may have extraction
67
+ if (!check.run_id ||
68
+ !check.workflow ||
69
+ !check.started_at ||
70
+ !check.duration) {
71
+ continue; // Skip invalid checks
72
+ }
73
+ const actionCheck = {
74
+ name: check.name,
75
+ status: check.status,
76
+ conclusion: check.conclusion,
77
+ run_id: check.run_id,
78
+ workflow: check.workflow,
79
+ started_at: check.started_at,
80
+ duration: check.duration,
81
+ };
82
+ // Try to extract errors if check failed
83
+ if (check.conclusion === 'failure' && check.run_id) {
84
+ // Use retry logic to handle GitHub API race condition (Issue #4)
85
+ const logs = await this.fetchLogsWithRetry(check.run_id);
86
+ if (logs) {
87
+ const extraction = await this.extractionDetector.detectAndExtract(actionCheck, logs);
88
+ if (extraction) {
89
+ actionCheck.extraction = extraction;
90
+ }
91
+ // Save logs to cache
92
+ if (this.cacheManager) {
93
+ await this.cacheManager.saveLog(check.run_id, logs);
94
+ if (extraction) {
95
+ await this.cacheManager.saveExtraction(check.run_id, extraction);
96
+ }
97
+ }
98
+ }
99
+ // If logs are null, gracefully continue without extraction
100
+ // No noisy error output (Issue #4 fix)
101
+ }
102
+ githubActions.push(actionCheck);
103
+ }
104
+ else {
105
+ // External check - will extract later
106
+ if (!check.url) {
107
+ continue; // Skip invalid checks
108
+ }
109
+ rawExternalChecks.push({
110
+ name: check.name,
111
+ status: check.status,
112
+ conclusion: check.conclusion,
113
+ url: check.url,
114
+ provider: check.provider,
115
+ });
116
+ }
117
+ }
118
+ // Extract details from external checks (all at once)
119
+ const externalChecks = await this.externalCheckExtractor.extractAll(rawExternalChecks);
120
+ // Order checks: failed first (newspaper philosophy)
121
+ const orderedGitHubActions = this.orderChecks(githubActions);
122
+ const orderedExternalChecks = this.orderExternalChecks(externalChecks);
123
+ // Calculate check counts
124
+ const totalChecks = githubActions.length + externalChecks.length;
125
+ const passedChecks = githubActions.filter((c) => c.conclusion === 'success').length +
126
+ externalChecks.filter((c) => c.conclusion === 'success').length;
127
+ const failedChecks = githubActions.filter((c) => c.conclusion === 'failure').length +
128
+ externalChecks.filter((c) => c.conclusion === 'failure').length;
129
+ const pendingChecks = githubActions.filter((c) => c.status !== 'completed').length +
130
+ externalChecks.filter((c) => c.status !== 'completed').length;
131
+ // Fetch history summary
132
+ const historySummary = await this.historyBuilder.buildSummary(prMetadata.branch);
133
+ // Fetch file changes
134
+ const changes = await this.fetcher.fetchFileChanges(prNumber);
135
+ // Determine overall status
136
+ let status = 'passed';
137
+ if (failedChecks > 0) {
138
+ status = 'failed';
139
+ }
140
+ else if (pendingChecks > 0) {
141
+ status = 'pending';
142
+ }
143
+ // Generate guidance
144
+ const guidance = this.generateGuidance(status, orderedGitHubActions, orderedExternalChecks, prMetadata.mergeable);
145
+ // Build result
146
+ const result = {
147
+ pr: prMetadata,
148
+ status,
149
+ checks: {
150
+ total: totalChecks,
151
+ passed: passedChecks,
152
+ failed: failedChecks,
153
+ pending: pendingChecks,
154
+ history_summary: historySummary.total_runs > 0 ? historySummary : undefined,
155
+ github_actions: orderedGitHubActions,
156
+ external_checks: orderedExternalChecks,
157
+ },
158
+ changes,
159
+ guidance,
160
+ // Note: cache field removed - will be added back when actually needed
161
+ };
162
+ // Note: We do NOT cache the result itself - only logs are cached
163
+ // This ensures PR status is always fresh from GitHub
164
+ return result;
165
+ }
166
+ /**
167
+ * Build result for a specific run ID
168
+ *
169
+ * Useful for watching specific failed runs to test extraction.
170
+ * Does not use history summary (since it's a single run).
171
+ *
172
+ * @param prNumber - PR number
173
+ * @param runId - GitHub run ID
174
+ * @param options - Options (useCache)
175
+ * @returns WatchPRResult with single check
176
+ */
177
+ async buildResultForRun(prNumber, runId, options = {}) {
178
+ const { useCache = false } = options;
179
+ // Initialize cache manager if caching enabled
180
+ if (useCache && !this.cacheManager) {
181
+ this.cacheManager = new CacheManager(`${this.owner}/${this.repo}`, prNumber);
182
+ }
183
+ // Fetch PR metadata (still needed for context)
184
+ const prMetadata = await this.fetcher.fetchPRDetails(prNumber);
185
+ // Fetch specific run details
186
+ const runDetails = await this.fetcher.fetchRunDetails(runId);
187
+ // Build GitHub Action check from run details
188
+ const actionCheck = {
189
+ name: runDetails.name,
190
+ status: runDetails.status,
191
+ conclusion: runDetails.conclusion,
192
+ run_id: runDetails.run_id,
193
+ workflow: runDetails.workflow,
194
+ started_at: runDetails.started_at,
195
+ duration: runDetails.duration,
196
+ };
197
+ // Try to extract errors from logs (with retry logic for Issue #4)
198
+ const logs = await this.fetchLogsWithRetry(runId);
199
+ if (logs) {
200
+ const extraction = await this.extractionDetector.detectAndExtract(actionCheck, logs);
201
+ if (extraction) {
202
+ actionCheck.extraction = extraction;
203
+ }
204
+ // Save logs to cache (extraction can be re-run later)
205
+ if (this.cacheManager) {
206
+ await this.cacheManager.saveLog(runId, logs);
207
+ if (extraction) {
208
+ await this.cacheManager.saveExtraction(runId, extraction);
209
+ }
210
+ }
211
+ }
212
+ // If logs are null, gracefully continue without extraction
213
+ // No noisy error output (Issue #4 fix)
214
+ // Fetch file changes (for context)
215
+ const changes = await this.fetcher.fetchFileChanges(prNumber);
216
+ // Determine status from the single check
217
+ let status = 'passed';
218
+ if (actionCheck.conclusion === 'failure') {
219
+ status = 'failed';
220
+ }
221
+ else if (actionCheck.status === 'in_progress' || actionCheck.status === 'queued') {
222
+ status = 'pending';
223
+ }
224
+ // Calculate check counts (single check)
225
+ const totalChecks = 1;
226
+ const passedChecks = actionCheck.conclusion === 'success' ? 1 : 0;
227
+ const failedChecks = actionCheck.conclusion === 'failure' ? 1 : 0;
228
+ const pendingChecks = actionCheck.status === 'in_progress' || actionCheck.status === 'queued' ? 1 : 0;
229
+ // Generate guidance (simplified for single run)
230
+ const guidance = this.generateGuidance(status, [actionCheck], [], prMetadata.mergeable);
231
+ // Build result
232
+ const result = {
233
+ pr: prMetadata,
234
+ status,
235
+ checks: {
236
+ total: totalChecks,
237
+ passed: passedChecks,
238
+ failed: failedChecks,
239
+ pending: pendingChecks,
240
+ github_actions: [actionCheck],
241
+ external_checks: [],
242
+ },
243
+ changes,
244
+ guidance,
245
+ // Note: cache field removed - will be added back when actually needed
246
+ };
247
+ // Don't cache metadata for single-run mode (historical runs are immutable)
248
+ // But logs and extractions are already cached above
249
+ return result;
250
+ }
251
+ /**
252
+ * Get priority for check ordering (lower is higher priority)
253
+ */
254
+ getCheckPriority(conclusion, status) {
255
+ if (conclusion === 'failure')
256
+ return 0;
257
+ if (status !== 'completed')
258
+ return 1;
259
+ if (conclusion === 'success')
260
+ return 2;
261
+ return 3;
262
+ }
263
+ /**
264
+ * Order checks: failed first, then pending, then passed
265
+ *
266
+ * @param checks - GitHub Action checks
267
+ * @returns Ordered checks
268
+ */
269
+ orderChecks(checks) {
270
+ return checks.sort((a, b) => {
271
+ return this.getCheckPriority(a.conclusion, a.status) - this.getCheckPriority(b.conclusion, b.status);
272
+ });
273
+ }
274
+ /**
275
+ * Order external checks: failed first, then pending, then passed
276
+ *
277
+ * @param checks - External checks
278
+ * @returns Ordered checks
279
+ */
280
+ // eslint-disable-next-line sonarjs/no-identical-functions
281
+ orderExternalChecks(checks) {
282
+ return checks.sort((a, b) => {
283
+ return this.getCheckPriority(a.conclusion, a.status) - this.getCheckPriority(b.conclusion, b.status);
284
+ });
285
+ }
286
+ /**
287
+ * Generate intelligent guidance based on check results
288
+ *
289
+ * @param status - Overall status
290
+ * @param githubActions - GitHub Action checks
291
+ * @param externalChecks - External checks
292
+ * @param mergeable - Is PR mergeable?
293
+ * @returns Guidance with next steps
294
+ */
295
+ generateGuidance(status, githubActions, externalChecks, mergeable) {
296
+ const nextSteps = [];
297
+ if (status === 'failed') {
298
+ // Find failed checks
299
+ const failedGitHubActions = githubActions.filter((c) => c.conclusion === 'failure');
300
+ const failedExternalChecks = externalChecks.filter((c) => c.conclusion === 'failure');
301
+ // Add next steps for failed GitHub Actions
302
+ for (const check of failedGitHubActions) {
303
+ nextSteps.push({
304
+ action: `Fix ${check.name} failure`,
305
+ url: `https://github.com/${this.owner}/${this.repo}/actions/runs/${check.run_id}`,
306
+ severity: 'error',
307
+ reason: check.extraction
308
+ ? `${check.extraction.totalErrors} error(s) detected`
309
+ : 'Check failed',
310
+ });
311
+ }
312
+ // Add next steps for failed external checks
313
+ for (const check of failedExternalChecks) {
314
+ nextSteps.push({
315
+ action: `Fix ${check.name} failure`,
316
+ url: check.url,
317
+ severity: check.extracted?.severity ?? 'error',
318
+ reason: check.extracted?.summary ?? 'Check failed',
319
+ });
320
+ }
321
+ return {
322
+ status: 'failed',
323
+ blocking: !mergeable,
324
+ severity: 'error',
325
+ summary: `${failedGitHubActions.length + failedExternalChecks.length} check(s) failed`,
326
+ next_steps: nextSteps,
327
+ };
328
+ }
329
+ if (status === 'pending') {
330
+ return {
331
+ status: 'pending',
332
+ blocking: false,
333
+ severity: 'info',
334
+ summary: 'Checks are still running',
335
+ next_steps: [
336
+ {
337
+ action: 'Wait for checks to complete',
338
+ severity: 'info',
339
+ },
340
+ ],
341
+ };
342
+ }
343
+ // Passed
344
+ return {
345
+ status: 'passed',
346
+ blocking: false,
347
+ severity: 'info',
348
+ summary: 'All checks passed',
349
+ next_steps: mergeable
350
+ ? [
351
+ {
352
+ action: 'Ready to merge',
353
+ severity: 'info',
354
+ },
355
+ ]
356
+ : [
357
+ {
358
+ action: 'Resolve merge conflicts',
359
+ severity: 'warning',
360
+ reason: 'PR is not mergeable',
361
+ },
362
+ ],
363
+ };
364
+ }
365
+ // buildCacheInfo() removed - cache field will be added back when actually needed
366
+ /**
367
+ * Fetch logs with retry logic for race conditions
368
+ *
369
+ * When GitHub marks a check as complete, logs may not be immediately available.
370
+ * This method retries with exponential backoff to handle the race condition.
371
+ *
372
+ * Retry schedule: 2s, 4s, 8s (total 3 attempts over ~14 seconds)
373
+ *
374
+ * @param runId - GitHub run ID
375
+ * @param maxRetries - Maximum number of retry attempts (default: 3)
376
+ * @returns Log content, or null if all retries failed
377
+ */
378
+ async fetchLogsWithRetry(runId, maxRetries = 3) {
379
+ for (let attempt = 1; attempt <= maxRetries; attempt++) {
380
+ try {
381
+ return await this.fetcher.fetchRunLogs(runId);
382
+ }
383
+ catch {
384
+ // Intentionally suppress error (Issue #4 fix: no noisy output)
385
+ // If this was the last attempt, break without sleeping
386
+ if (attempt === maxRetries) {
387
+ break;
388
+ }
389
+ // Exponential backoff: 2s, 4s, 8s
390
+ const delayMs = Math.pow(2, attempt) * 1000;
391
+ await new Promise((resolve) => setTimeout(resolve, delayMs));
392
+ }
393
+ }
394
+ // All retries failed - return null (graceful degradation)
395
+ // Logs can be inspected with debug mode if needed
396
+ return null;
397
+ }
398
+ /**
399
+ * Fetch all workflow runs for a PR (for --history flag)
400
+ *
401
+ * @param prNumber - PR number
402
+ * @returns List of workflow runs with basic metadata
403
+ */
404
+ async fetchRunsForPR(prNumber) {
405
+ return await this.fetcher.fetchRunsForPR(prNumber);
406
+ }
407
+ /**
408
+ * Determine if output should be YAML format
409
+ *
410
+ * Auto-YAML on failure (consistent with validate command)
411
+ *
412
+ * @param status - Overall status
413
+ * @param forceYAML - Force YAML output
414
+ * @returns True if should output YAML
415
+ */
416
+ shouldOutputYAML(status, forceYAML) {
417
+ return forceYAML || status === 'failed';
418
+ }
419
+ }
420
+ //# sourceMappingURL=watch-pr-orchestrator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"watch-pr-orchestrator.js","sourceRoot":"","sources":["../../src/services/watch-pr-orchestrator.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAYH,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EACL,gBAAgB,EAChB,yBAAyB,EACzB,mBAAmB,GACpB,MAAM,+BAA+B,CAAC;AACvC,OAAO,EAAE,sBAAsB,EAAE,MAAM,+BAA+B,CAAC;AACvE,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AACpD,OAAO,EAAE,qBAAqB,EAAE,MAAM,8BAA8B,CAAC;AAErE;;GAEG;AACH,MAAM,OAAO,mBAAmB;IAQX;IACA;IARF,OAAO,CAAgB;IACvB,cAAc,CAAwB;IACtC,kBAAkB,CAAyB;IAC3C,sBAAsB,CAA4B;IAC3D,YAAY,CAAgB;IAEpC,YACmB,KAAa,EACb,IAAY;QADZ,UAAK,GAAL,KAAK,CAAQ;QACb,SAAI,GAAJ,IAAI,CAAQ;QAE7B,IAAI,CAAC,OAAO,GAAG,IAAI,aAAa,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;QAC9C,IAAI,CAAC,cAAc,GAAG,IAAI,qBAAqB,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;QAC7D,IAAI,CAAC,kBAAkB,GAAG,IAAI,sBAAsB,EAAE,CAAC;QAEvD,+CAA+C;QAC/C,IAAI,CAAC,sBAAsB,GAAG,IAAI,yBAAyB,EAAE,CAAC;QAC9D,IAAI,CAAC,sBAAsB,CAAC,QAAQ,CAAC,IAAI,gBAAgB,EAAE,CAAC,CAAC;QAC7D,IAAI,CAAC,sBAAsB,CAAC,QAAQ,CAAC,IAAI,mBAAmB,EAAE,CAAC,CAAC;IAClE,CAAC;IAED;;;;;;OAMG;IACH,wDAAwD;IACxD,KAAK,CAAC,WAAW,CACf,QAAgB,EAChB,UAAwD,EAAE;QAE1D,MAAM,EAAE,QAAQ,GAAG,IAAI,EAAE,GAAG,OAAO,CAAC;QAEpC,8DAA8D;QAC9D,IAAI,QAAQ,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE,CAAC;YACnC,IAAI,CAAC,YAAY,GAAG,IAAI,YAAY,CAAC,GAAG,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,IAAI,EAAE,EAAE,QAAQ,CAAC,CAAC;QAC/E,CAAC;QAED,wDAAwD;QACxD,iEAAiE;QACjE,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;QAE/D,eAAe;QACf,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC;QAExD,kDAAkD;QAClD,MAAM,aAAa,GAAwB,EAAE,CAAC;QAC9C,MAAM,iBAAiB,GAAoB,EAAE,CAAC;QAE9C,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YAC3B,IAAI,KAAK,CAAC,IAAI,KAAK,eAAe,EAAE,CAAC;gBACnC,4CAA4C;gBAC5C,IACE,CAAC,KAAK,CAAC,MAAM;oBACb,CAAC,KAAK,CAAC,QAAQ;oBACf,CAAC,KAAK,CAAC,UAAU;oBACjB,CAAC,KAAK,CAAC,QAAQ,EACf,CAAC;oBACD,SAAS,CAAC,sBAAsB;gBAClC,CAAC;gBAED,MAAM,WAAW,GAAsB;oBACrC,IAAI,EAAE,KAAK,CAAC,IAAI;oBAChB,MAAM,EAAE,KAAK,CAAC,MAAM;oBACpB,UAAU,EAAE,KAAK,CAAC,UAAU;oBAC5B,MAAM,EAAE,KAAK,CAAC,MAAM;oBACpB,QAAQ,EAAE,KAAK,CAAC,QAAQ;oBACxB,UAAU,EAAE,KAAK,CAAC,UAAU;oBAC5B,QAAQ,EAAE,KAAK,CAAC,QAAQ;iBACzB,CAAC;gBAEF,wCAAwC;gBACxC,IAAI,KAAK,CAAC,UAAU,KAAK,SAAS,IAAI,KAAK,CAAC,MAAM,EAAE,CAAC;oBACnD,iEAAiE;oBACjE,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,kBAAkB,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;oBACzD,IAAI,IAAI,EAAE,CAAC;wBACT,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,kBAAkB,CAAC,gBAAgB,CAAC,WAAW,EAAE,IAAI,CAAC,CAAC;wBACrF,IAAI,UAAU,EAAE,CAAC;4BACf,WAAW,CAAC,UAAU,GAAG,UAAU,CAAC;wBACtC,CAAC;wBAED,qBAAqB;wBACrB,IAAI,IAAI,CAAC,YAAY,EAAE,CAAC;4BACtB,MAAM,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC,KAAK,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;4BACpD,IAAI,UAAU,EAAE,CAAC;gCACf,MAAM,IAAI,CAAC,YAAY,CAAC,cAAc,CAAC,KAAK,CAAC,MAAM,EAAE,UAAU,CAAC,CAAC;4BACnE,CAAC;wBACH,CAAC;oBACH,CAAC;oBACD,2DAA2D;oBAC3D,uCAAuC;gBACzC,CAAC;gBAED,aAAa,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;YAClC,CAAC;iBAAM,CAAC;gBACN,sCAAsC;gBACtC,IAAI,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC;oBACf,SAAS,CAAC,sBAAsB;gBAClC,CAAC;gBAED,iBAAiB,CAAC,IAAI,CAAC;oBACrB,IAAI,EAAE,KAAK,CAAC,IAAI;oBAChB,MAAM,EAAE,KAAK,CAAC,MAAM;oBACpB,UAAU,EAAE,KAAK,CAAC,UAAU;oBAC5B,GAAG,EAAE,KAAK,CAAC,GAAG;oBACd,QAAQ,EAAE,KAAK,CAAC,QAAQ;iBACzB,CAAC,CAAC;YACL,CAAC;QACH,CAAC;QAED,qDAAqD;QACrD,MAAM,cAAc,GAAG,MAAM,IAAI,CAAC,sBAAsB,CAAC,UAAU,CAAC,iBAAiB,CAAC,CAAC;QAEvF,oDAAoD;QACpD,MAAM,oBAAoB,GAAG,IAAI,CAAC,WAAW,CAAC,aAAa,CAAC,CAAC;QAC7D,MAAM,qBAAqB,GAAG,IAAI,CAAC,mBAAmB,CAAC,cAAc,CAAC,CAAC;QAEvE,yBAAyB;QACzB,MAAM,WAAW,GAAG,aAAa,CAAC,MAAM,GAAG,cAAc,CAAC,MAAM,CAAC;QACjE,MAAM,YAAY,GAChB,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,MAAM;YAC9D,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,MAAM,CAAC;QAClE,MAAM,YAAY,GAChB,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,MAAM;YAC9D,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,MAAM,CAAC;QAClE,MAAM,aAAa,GACjB,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,WAAW,CAAC,CAAC,MAAM;YAC5D,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,WAAW,CAAC,CAAC,MAAM,CAAC;QAEhE,wBAAwB;QACxB,MAAM,cAAc,GAAG,MAAM,IAAI,CAAC,cAAc,CAAC,YAAY,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC;QAEjF,qBAAqB;QACrB,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,gBAAgB,CAAC,QAAQ,CAAC,CAAC;QAE9D,2BAA2B;QAC3B,IAAI,MAAM,GAAa,QAAQ,CAAC;QAChC,IAAI,YAAY,GAAG,CAAC,EAAE,CAAC;YACrB,MAAM,GAAG,QAAQ,CAAC;QACpB,CAAC;aAAM,IAAI,aAAa,GAAG,CAAC,EAAE,CAAC;YAC7B,MAAM,GAAG,SAAS,CAAC;QACrB,CAAC;QAED,oBAAoB;QACpB,MAAM,QAAQ,GAAG,IAAI,CAAC,gBAAgB,CACpC,MAAM,EACN,oBAAoB,EACpB,qBAAqB,EACrB,UAAU,CAAC,SAAS,CACrB,CAAC;QAEF,eAAe;QACf,MAAM,MAAM,GAAkB;YAC5B,EAAE,EAAE,UAAU;YACd,MAAM;YACN,MAAM,EAAE;gBACN,KAAK,EAAE,WAAW;gBAClB,MAAM,EAAE,YAAY;gBACpB,MAAM,EAAE,YAAY;gBACpB,OAAO,EAAE,aAAa;gBACtB,eAAe,EAAE,cAAc,CAAC,UAAU,GAAG,CAAC,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,SAAS;gBAC3E,cAAc,EAAE,oBAAoB;gBACpC,eAAe,EAAE,qBAAqB;aACvC;YACD,OAAO;YACP,QAAQ;YACR,sEAAsE;SACvE,CAAC;QAEF,iEAAiE;QACjE,qDAAqD;QAErD,OAAO,MAAM,CAAC;IAChB,CAAC;IAED;;;;;;;;;;OAUG;IACH,KAAK,CAAC,iBAAiB,CACrB,QAAgB,EAChB,KAAa,EACb,UAAkC,EAAE;QAEpC,MAAM,EAAE,QAAQ,GAAG,KAAK,EAAE,GAAG,OAAO,CAAC;QAErC,8CAA8C;QAC9C,IAAI,QAAQ,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE,CAAC;YACnC,IAAI,CAAC,YAAY,GAAG,IAAI,YAAY,CAAC,GAAG,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,IAAI,EAAE,EAAE,QAAQ,CAAC,CAAC;QAC/E,CAAC;QAED,+CAA+C;QAC/C,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;QAE/D,6BAA6B;QAC7B,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,eAAe,CAAC,KAAK,CAAC,CAAC;QAE7D,6CAA6C;QAC7C,MAAM,WAAW,GAAsB;YACrC,IAAI,EAAE,UAAU,CAAC,IAAI;YACrB,MAAM,EAAE,UAAU,CAAC,MAAM;YACzB,UAAU,EAAE,UAAU,CAAC,UAAU;YACjC,MAAM,EAAE,UAAU,CAAC,MAAM;YACzB,QAAQ,EAAE,UAAU,CAAC,QAAQ;YAC7B,UAAU,EAAE,UAAU,CAAC,UAAU;YACjC,QAAQ,EAAE,UAAU,CAAC,QAAQ;SAC9B,CAAC;QAEF,kEAAkE;QAClE,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,kBAAkB,CAAC,KAAK,CAAC,CAAC;QAClD,IAAI,IAAI,EAAE,CAAC;YACT,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,kBAAkB,CAAC,gBAAgB,CAAC,WAAW,EAAE,IAAI,CAAC,CAAC;YACrF,IAAI,UAAU,EAAE,CAAC;gBACf,WAAW,CAAC,UAAU,GAAG,UAAU,CAAC;YACtC,CAAC;YAED,sDAAsD;YACtD,IAAI,IAAI,CAAC,YAAY,EAAE,CAAC;gBACtB,MAAM,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;gBAC7C,IAAI,UAAU,EAAE,CAAC;oBACf,MAAM,IAAI,CAAC,YAAY,CAAC,cAAc,CAAC,KAAK,EAAE,UAAU,CAAC,CAAC;gBAC5D,CAAC;YACH,CAAC;QACH,CAAC;QACD,2DAA2D;QAC3D,uCAAuC;QAEvC,mCAAmC;QACnC,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,gBAAgB,CAAC,QAAQ,CAAC,CAAC;QAE9D,yCAAyC;QACzC,IAAI,MAAM,GAAa,QAAQ,CAAC;QAChC,IAAI,WAAW,CAAC,UAAU,KAAK,SAAS,EAAE,CAAC;YACzC,MAAM,GAAG,QAAQ,CAAC;QACpB,CAAC;aAAM,IAAI,WAAW,CAAC,MAAM,KAAK,aAAa,IAAI,WAAW,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;YACnF,MAAM,GAAG,SAAS,CAAC;QACrB,CAAC;QAED,wCAAwC;QACxC,MAAM,WAAW,GAAG,CAAC,CAAC;QACtB,MAAM,YAAY,GAAG,WAAW,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAClE,MAAM,YAAY,GAAG,WAAW,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAClE,MAAM,aAAa,GAAG,WAAW,CAAC,MAAM,KAAK,aAAa,IAAI,WAAW,CAAC,MAAM,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAEtG,gDAAgD;QAChD,MAAM,QAAQ,GAAG,IAAI,CAAC,gBAAgB,CAAC,MAAM,EAAE,CAAC,WAAW,CAAC,EAAE,EAAE,EAAE,UAAU,CAAC,SAAS,CAAC,CAAC;QAExF,eAAe;QACf,MAAM,MAAM,GAAkB;YAC5B,EAAE,EAAE,UAAU;YACd,MAAM;YACN,MAAM,EAAE;gBACN,KAAK,EAAE,WAAW;gBAClB,MAAM,EAAE,YAAY;gBACpB,MAAM,EAAE,YAAY;gBACpB,OAAO,EAAE,aAAa;gBACtB,cAAc,EAAE,CAAC,WAAW,CAAC;gBAC7B,eAAe,EAAE,EAAE;aACpB;YACD,OAAO;YACP,QAAQ;YACR,sEAAsE;SACvE,CAAC;QAEF,2EAA2E;QAC3E,oDAAoD;QAEpD,OAAO,MAAM,CAAC;IAChB,CAAC;IAED;;OAEG;IACK,gBAAgB,CAAC,UAA4B,EAAE,MAAe;QACpE,IAAI,UAAU,KAAK,SAAS;YAAE,OAAO,CAAC,CAAC;QACvC,IAAI,MAAM,KAAK,WAAW;YAAE,OAAO,CAAC,CAAC;QACrC,IAAI,UAAU,KAAK,SAAS;YAAE,OAAO,CAAC,CAAC;QACvC,OAAO,CAAC,CAAC;IACX,CAAC;IAED;;;;;OAKG;IACK,WAAW,CAAC,MAA2B;QAC7C,OAAO,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;YAC1B,OAAO,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,MAAM,CAAC,GAAG,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC;QACvG,CAAC,CAAC,CAAC;IACL,CAAC;IAED;;;;;OAKG;IACH,0DAA0D;IAClD,mBAAmB,CAAC,MAAuB;QACjD,OAAO,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;YAC1B,OAAO,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,MAAM,CAAC,GAAG,IAAI,CAAC,gBAAgB,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC;QACvG,CAAC,CAAC,CAAC;IACL,CAAC;IAED;;;;;;;;OAQG;IACK,gBAAgB,CACtB,MAAuC,EACvC,aAAkC,EAClC,cAA+B,EAC/B,SAAkB;QAElB,MAAM,SAAS,GAAe,EAAE,CAAC;QAEjC,IAAI,MAAM,KAAK,QAAQ,EAAE,CAAC;YACxB,qBAAqB;YACrB,MAAM,mBAAmB,GAAG,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC;YACpF,MAAM,oBAAoB,GAAG,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC;YAEtF,2CAA2C;YAC3C,KAAK,MAAM,KAAK,IAAI,mBAAmB,EAAE,CAAC;gBACxC,SAAS,CAAC,IAAI,CAAC;oBACb,MAAM,EAAE,OAAO,KAAK,CAAC,IAAI,UAAU;oBACnC,GAAG,EAAE,sBAAsB,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,IAAI,iBAAiB,KAAK,CAAC,MAAM,EAAE;oBACjF,QAAQ,EAAE,OAAO;oBACjB,MAAM,EAAE,KAAK,CAAC,UAAU;wBACtB,CAAC,CAAC,GAAG,KAAK,CAAC,UAAU,CAAC,WAAW,oBAAoB;wBACrD,CAAC,CAAC,cAAc;iBACnB,CAAC,CAAC;YACL,CAAC;YAED,4CAA4C;YAC5C,KAAK,MAAM,KAAK,IAAI,oBAAoB,EAAE,CAAC;gBACzC,SAAS,CAAC,IAAI,CAAC;oBACb,MAAM,EAAE,OAAO,KAAK,CAAC,IAAI,UAAU;oBACnC,GAAG,EAAE,KAAK,CAAC,GAAG;oBACd,QAAQ,EAAE,KAAK,CAAC,SAAS,EAAE,QAAQ,IAAI,OAAO;oBAC9C,MAAM,EAAE,KAAK,CAAC,SAAS,EAAE,OAAO,IAAI,cAAc;iBACnD,CAAC,CAAC;YACL,CAAC;YAED,OAAO;gBACL,MAAM,EAAE,QAAQ;gBAChB,QAAQ,EAAE,CAAC,SAAS;gBACpB,QAAQ,EAAE,OAAO;gBACjB,OAAO,EAAE,GAAG,mBAAmB,CAAC,MAAM,GAAG,oBAAoB,CAAC,MAAM,kBAAkB;gBACtF,UAAU,EAAE,SAAS;aACtB,CAAC;QACJ,CAAC;QAED,IAAI,MAAM,KAAK,SAAS,EAAE,CAAC;YACzB,OAAO;gBACL,MAAM,EAAE,SAAS;gBACjB,QAAQ,EAAE,KAAK;gBACf,QAAQ,EAAE,MAAM;gBAChB,OAAO,EAAE,0BAA0B;gBACnC,UAAU,EAAE;oBACV;wBACE,MAAM,EAAE,6BAA6B;wBACrC,QAAQ,EAAE,MAAM;qBACjB;iBACF;aACF,CAAC;QACJ,CAAC;QAED,SAAS;QACT,OAAO;YACL,MAAM,EAAE,QAAQ;YAChB,QAAQ,EAAE,KAAK;YACf,QAAQ,EAAE,MAAM;YAChB,OAAO,EAAE,mBAAmB;YAC5B,UAAU,EAAE,SAAS;gBACnB,CAAC,CAAC;oBACE;wBACE,MAAM,EAAE,gBAAgB;wBACxB,QAAQ,EAAE,MAAM;qBACjB;iBACF;gBACH,CAAC,CAAC;oBACE;wBACE,MAAM,EAAE,yBAAyB;wBACjC,QAAQ,EAAE,SAAS;wBACnB,MAAM,EAAE,qBAAqB;qBAC9B;iBACF;SACN,CAAC;IACJ,CAAC;IAED,iFAAiF;IAEjF;;;;;;;;;;;OAWG;IACK,KAAK,CAAC,kBAAkB,CAAC,KAAa,EAAE,UAAU,GAAG,CAAC;QAC5D,KAAK,IAAI,OAAO,GAAG,CAAC,EAAE,OAAO,IAAI,UAAU,EAAE,OAAO,EAAE,EAAE,CAAC;YACvD,IAAI,CAAC;gBACH,OAAO,MAAM,IAAI,CAAC,OAAO,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC;YAChD,CAAC;YAAC,MAAM,CAAC;gBACP,+DAA+D;gBAC/D,uDAAuD;gBACvD,IAAI,OAAO,KAAK,UAAU,EAAE,CAAC;oBAC3B,MAAM;gBACR,CAAC;gBAED,kCAAkC;gBAClC,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC,GAAG,IAAI,CAAC;gBAC5C,MAAM,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC,CAAC;YAC/D,CAAC;QACH,CAAC;QAED,0DAA0D;QAC1D,kDAAkD;QAClD,OAAO,IAAI,CAAC;IACd,CAAC;IAED;;;;;OAKG;IACH,KAAK,CAAC,cAAc,CAAC,QAAgB;QAQnC,OAAO,MAAM,IAAI,CAAC,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;IACrD,CAAC;IAED;;;;;;;;OAQG;IACH,gBAAgB,CAAC,MAAc,EAAE,SAAkB;QACjD,OAAO,SAAS,IAAI,MAAM,KAAK,QAAQ,CAAC;IAC1C,CAAC;CACF"}
@@ -0,0 +1,21 @@
1
+ /**
2
+ * Command name detection utilities
3
+ *
4
+ * Detects the actual command name used to invoke vibe-validate (e.g., "vv" vs "vibe-validate")
5
+ * so error messages and usage examples reflect what the user actually typed.
6
+ */
7
+ /**
8
+ * Get the command name that was used to invoke the CLI
9
+ *
10
+ * @returns The command name (e.g., "vv", "vibe-validate", or fallback "vibe-validate")
11
+ *
12
+ * @example
13
+ * ```typescript
14
+ * const cmd = getCommandName();
15
+ * console.error(`Usage: ${cmd} watch-pr <pr-number>`);
16
+ * // If invoked with "vv": "Usage: vv watch-pr <pr-number>"
17
+ * // If invoked with "vibe-validate": "Usage: vibe-validate watch-pr <pr-number>"
18
+ * ```
19
+ */
20
+ export declare function getCommandName(): string;
21
+ //# sourceMappingURL=command-name.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"command-name.d.ts","sourceRoot":"","sources":["../../src/utils/command-name.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH;;;;;;;;;;;;GAYG;AACH,wBAAgB,cAAc,IAAI,MAAM,CA4BvC"}
@@ -0,0 +1,45 @@
1
+ /**
2
+ * Command name detection utilities
3
+ *
4
+ * Detects the actual command name used to invoke vibe-validate (e.g., "vv" vs "vibe-validate")
5
+ * so error messages and usage examples reflect what the user actually typed.
6
+ */
7
+ import { basename } from 'node:path';
8
+ /**
9
+ * Get the command name that was used to invoke the CLI
10
+ *
11
+ * @returns The command name (e.g., "vv", "vibe-validate", or fallback "vibe-validate")
12
+ *
13
+ * @example
14
+ * ```typescript
15
+ * const cmd = getCommandName();
16
+ * console.error(`Usage: ${cmd} watch-pr <pr-number>`);
17
+ * // If invoked with "vv": "Usage: vv watch-pr <pr-number>"
18
+ * // If invoked with "vibe-validate": "Usage: vibe-validate watch-pr <pr-number>"
19
+ * ```
20
+ */
21
+ export function getCommandName() {
22
+ // Check if the wrapper passed the command name via environment variable
23
+ // This is set by the smart wrapper (bin/vibe-validate.ts) when it spawns bin.js
24
+ const envCommandName = process.env.VV_COMMAND_NAME;
25
+ if (envCommandName === 'vv' || envCommandName === 'vibe-validate') {
26
+ return envCommandName;
27
+ }
28
+ // Fallback: extract from process.argv[1] (for direct invocation or dev mode)
29
+ // process.argv[0] is node executable
30
+ // process.argv[1] is the script being executed (e.g., /path/to/vv or /path/to/vibe-validate)
31
+ const scriptPath = process.argv[1];
32
+ if (!scriptPath) {
33
+ return 'vibe-validate'; // Fallback
34
+ }
35
+ // Extract basename (e.g., "vv" from "/usr/local/bin/vv")
36
+ const commandName = basename(scriptPath);
37
+ // Handle common cases: vv, vibe-validate, or .js/.ts extensions in dev mode
38
+ if (commandName === 'vv' || commandName === 'vibe-validate') {
39
+ return commandName;
40
+ }
41
+ // Dev mode: might be bin.js, bin.ts, vibe-validate.js, etc.
42
+ // Fall back to "vibe-validate" for consistency
43
+ return 'vibe-validate';
44
+ }
45
+ //# sourceMappingURL=command-name.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"command-name.js","sourceRoot":"","sources":["../../src/utils/command-name.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AAErC;;;;;;;;;;;;GAYG;AACH,MAAM,UAAU,cAAc;IAC5B,wEAAwE;IACxE,gFAAgF;IAChF,MAAM,cAAc,GAAG,OAAO,CAAC,GAAG,CAAC,eAAe,CAAC;IACnD,IAAI,cAAc,KAAK,IAAI,IAAI,cAAc,KAAK,eAAe,EAAE,CAAC;QAClE,OAAO,cAAc,CAAC;IACxB,CAAC;IAED,6EAA6E;IAC7E,qCAAqC;IACrC,6FAA6F;IAC7F,MAAM,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAEnC,IAAI,CAAC,UAAU,EAAE,CAAC;QAChB,OAAO,eAAe,CAAC,CAAC,WAAW;IACrC,CAAC;IAED,yDAAyD;IACzD,MAAM,WAAW,GAAG,QAAQ,CAAC,UAAU,CAAC,CAAC;IAEzC,4EAA4E;IAC5E,IAAI,WAAW,KAAK,IAAI,IAAI,WAAW,KAAK,eAAe,EAAE,CAAC;QAC5D,OAAO,WAAW,CAAC;IACrB,CAAC;IAED,4DAA4D;IAC5D,+CAA+C;IAC/C,OAAO,eAAe,CAAC;AACzB,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"pid-lock.d.ts","sourceRoot":"","sources":["../../src/utils/pid-lock.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAMH;;GAEG;AACH,MAAM,WAAW,QAAQ;IACvB,kCAAkC;IAClC,GAAG,EAAE,MAAM,CAAC;IACZ,6BAA6B;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,gDAAgD;IAChD,QAAQ,EAAE,MAAM,CAAC;IACjB,2CAA2C;IAC3C,SAAS,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,6CAA6C;IAC7C,QAAQ,EAAE,OAAO,CAAC;IAClB,wBAAwB;IACxB,QAAQ,EAAE,MAAM,CAAC;IACjB,8DAA8D;IAC9D,YAAY,CAAC,EAAE,QAAQ,CAAC;CACzB;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B;;;;OAIG;IACH,KAAK,CAAC,EAAE,WAAW,GAAG,SAAS,CAAC;IAChC;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AA8DD;;;;;;;;;;;GAWG;AACH,wBAAsB,WAAW,CAC/B,SAAS,EAAE,MAAM,EACjB,QAAQ,EAAE,MAAM,EAChB,OAAO,GAAE,WAAgB,GACxB,OAAO,CAAC,UAAU,CAAC,CAyCrB;AAED;;;;;;;GAOG;AACH,wBAAsB,WAAW,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAIjE;AAED;;;;;;;;;GASG;AACH,wBAAsB,SAAS,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,GAAE,WAAgB,GAAG,OAAO,CAAC,QAAQ,GAAG,IAAI,CAAC,CAuBtG;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,WAAW,CAC/B,SAAS,EAAE,MAAM,EACjB,cAAc,GAAE,MAAY,EAC5B,cAAc,GAAE,MAAa,EAC7B,OAAO,GAAE,WAAgB,GACxB,OAAO,CAAC;IAAE,QAAQ,EAAE,OAAO,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAC;IAAC,SAAS,EAAE,QAAQ,GAAG,IAAI,CAAA;CAAE,CAAC,CA6B/E"}
1
+ {"version":3,"file":"pid-lock.d.ts","sourceRoot":"","sources":["../../src/utils/pid-lock.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAQH;;GAEG;AACH,MAAM,WAAW,QAAQ;IACvB,kCAAkC;IAClC,GAAG,EAAE,MAAM,CAAC;IACZ,6BAA6B;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,gDAAgD;IAChD,QAAQ,EAAE,MAAM,CAAC;IACjB,2CAA2C;IAC3C,SAAS,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,6CAA6C;IAC7C,QAAQ,EAAE,OAAO,CAAC;IAClB,wBAAwB;IACxB,QAAQ,EAAE,MAAM,CAAC;IACjB,8DAA8D;IAC9D,YAAY,CAAC,EAAE,QAAQ,CAAC;CACzB;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B;;;;OAIG;IACH,KAAK,CAAC,EAAE,WAAW,GAAG,SAAS,CAAC;IAChC;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AA8DD;;;;;;;;;;;GAWG;AACH,wBAAsB,WAAW,CAC/B,SAAS,EAAE,MAAM,EACjB,QAAQ,EAAE,MAAM,EAChB,OAAO,GAAE,WAAgB,GACxB,OAAO,CAAC,UAAU,CAAC,CAyCrB;AAED;;;;;;;GAOG;AACH,wBAAsB,WAAW,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAIjE;AAED;;;;;;;;;GASG;AACH,wBAAsB,SAAS,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,GAAE,WAAgB,GAAG,OAAO,CAAC,QAAQ,GAAG,IAAI,CAAC,CAuBtG;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,WAAW,CAC/B,SAAS,EAAE,MAAM,EACjB,cAAc,GAAE,MAAY,EAC5B,cAAc,GAAE,MAAa,EAC7B,OAAO,GAAE,WAAgB,GACxB,OAAO,CAAC;IAAE,QAAQ,EAAE,OAAO,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAC;IAAC,SAAS,EAAE,QAAQ,GAAG,IAAI,CAAA;CAAE,CAAC,CA6B/E"}
@@ -5,8 +5,8 @@
5
5
  * Cross-platform (Node.js), works on Windows, macOS, Linux.
6
6
  */
7
7
  import { readFileSync, writeFileSync, unlinkSync, existsSync } from 'node:fs';
8
- import { tmpdir } from 'node:os';
9
8
  import { join } from 'node:path';
9
+ import { normalizedTmpdir } from '@vibe-validate/utils';
10
10
  /**
11
11
  * Encode directory path for use in lock file name
12
12
  *
@@ -40,11 +40,11 @@ function getLockFilePath(directory, options = {}) {
40
40
  throw new Error('projectId is required when scope is "project"');
41
41
  }
42
42
  // Project-scoped: /tmp/vibe-validate-project-{projectId}.lock
43
- return join(tmpdir(), `vibe-validate-project-${options.projectId}.lock`);
43
+ return join(normalizedTmpdir(), `vibe-validate-project-${options.projectId}.lock`);
44
44
  }
45
45
  // Directory-scoped (default): /tmp/vibe-validate-{encoded-dir}.lock
46
46
  const encoded = encodeDirectoryPath(directory);
47
- return join(tmpdir(), `vibe-validate-${encoded}.lock`);
47
+ return join(normalizedTmpdir(), `vibe-validate-${encoded}.lock`);
48
48
  }
49
49
  /**
50
50
  * Check if a process is running
@@ -1 +1 @@
1
- {"version":3,"file":"pid-lock.js","sourceRoot":"","sources":["../../src/utils/pid-lock.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"pid-lock.js","sourceRoot":"","sources":["../../src/utils/pid-lock.ts"],"names":[],"mappings":"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"}
@@ -60,7 +60,7 @@ export declare function formatToolName(tool: SecretScanningTool): string;
60
60
  /**
61
61
  * Show performance warning if scan was slow
62
62
  */
63
- export declare function showPerformanceWarning(tool: SecretScanningTool, duration: number, threshold: number): void;
63
+ export declare function showPerformanceWarning(tool: SecretScanningTool, duration: number, threshold: number, hasExplicitCommand?: boolean): void;
64
64
  /**
65
65
  * Show error message when secrets are detected
66
66
  */
@@ -1 +1 @@
1
- {"version":3,"file":"secret-scanning.d.ts","sourceRoot":"","sources":["../../src/utils/secret-scanning.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAQH;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG,UAAU,GAAG,YAAY,CAAC;AAE3D;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,kBAAkB,CAAC;IACzB,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;CACxB;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,GAAG,GAAE,MAAsB,GAAG,OAAO,CAKtE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,GAAE,MAAsB,GAAG,OAAO,CAExE;AAED;;GAEG;AACH,wBAAgB,yBAAyB,CAAC,GAAG,GAAE,MAAsB,GAAG,aAAa,EAAE,CAmBtF;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,WAAW,EAAE,MAAM,GAAG,SAAS,EAC/B,GAAG,GAAE,MAAsB,GAC1B;IAAE,IAAI,EAAE,kBAAkB,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,EAAE,CAoCjD;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,kBAAkB,CAAC;IACzB,MAAM,EAAE,OAAO,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,kBAAkB,EACxB,OAAO,EAAE,MAAM,EACf,OAAO,GAAE,OAAe,GACvB,UAAU,CAmEZ;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,kBAAkB,GAAG,MAAM,CAE/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,kBAAkB,EACxB,QAAQ,EAAE,MAAM,EAChB,SAAS,EAAE,MAAM,GAChB,IAAI,CAeN;AAED;;GAEG;AACH,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,UAAU,EAAE,GAAG,IAAI,CAsBpE"}
1
+ {"version":3,"file":"secret-scanning.d.ts","sourceRoot":"","sources":["../../src/utils/secret-scanning.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAQH;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG,UAAU,GAAG,YAAY,CAAC;AAE3D;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,kBAAkB,CAAC;IACzB,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;CACxB;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,GAAG,GAAE,MAAsB,GAAG,OAAO,CAKtE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,GAAE,MAAsB,GAAG,OAAO,CAExE;AAED;;GAEG;AACH,wBAAgB,yBAAyB,CAAC,GAAG,GAAE,MAAsB,GAAG,aAAa,EAAE,CAmBtF;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,WAAW,EAAE,MAAM,GAAG,SAAS,EAC/B,GAAG,GAAE,MAAsB,GAC1B;IAAE,IAAI,EAAE,kBAAkB,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,EAAE,CAoCjD;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,kBAAkB,CAAC;IACzB,MAAM,EAAE,OAAO,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,kBAAkB,EACxB,OAAO,EAAE,MAAM,EACf,OAAO,GAAE,OAAe,GACvB,UAAU,CA0FZ;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,kBAAkB,GAAG,MAAM,CAE/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,IAAI,EAAE,kBAAkB,EACxB,QAAQ,EAAE,MAAM,EAChB,SAAS,EAAE,MAAM,EACjB,kBAAkB,GAAE,OAAe,GAClC,IAAI,CAmBN;AAED;;GAEG;AACH,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,UAAU,EAAE,GAAG,IAAI,CAsBpE"}
@@ -40,7 +40,7 @@ export function detectSecretScanningTools(cwd = process.cwd()) {
40
40
  tool: 'secretlint',
41
41
  available: true, // Always available via npx
42
42
  hasConfig: secretlintConfigured,
43
- defaultCommand: 'npx secretlint "**/*"',
43
+ defaultCommand: 'npx secretlint .', // No glob patterns - safeExecFromString rejects them
44
44
  },
45
45
  ];
46
46
  }
@@ -85,7 +85,8 @@ export function selectToolsToRun(scanCommand, cwd = process.cwd()) {
85
85
  */
86
86
  export function runSecretScan(tool, command, verbose = false) {
87
87
  const startTime = Date.now();
88
- // Special handling for gitleaks - check availability first
88
+ // Special handling for gitleaks - skip if not installed (native binary, optional)
89
+ // secretlint is ALWAYS available via npx - never skip, always fail loud if error
89
90
  if (tool === 'gitleaks' && !isToolAvailable('gitleaks')) {
90
91
  return {
91
92
  tool,
@@ -96,6 +97,28 @@ export function runSecretScan(tool, command, verbose = false) {
96
97
  };
97
98
  }
98
99
  try {
100
+ // Parse and execute scanCommand string
101
+ //
102
+ // SECURITY: scanCommand comes from user config (vibe-validate.config.yaml)
103
+ // Same trust model as npm scripts - users control their own config files.
104
+ //
105
+ // LIMITATIONS:
106
+ // - Simple commands work: "gitleaks protect --staged"
107
+ // - Glob patterns FAIL: "npx secretlint **/*" (prevented by safeExecFromString)
108
+ // - Shell operators FAIL: "cmd1 && cmd2" (prevented by safeExecFromString)
109
+ // - Complex quoting FAILS: nested quotes, escapes (prevented by safeExecFromString)
110
+ //
111
+ // WHY safeExecFromString:
112
+ // - Handles simple quoted args: 'gitleaks protect --config ".gitleaks.toml"'
113
+ // - Fails fast on complex shell syntax (prevents silent bugs)
114
+ // - More robust than naive .split() which breaks with ANY quotes
115
+ //
116
+ // RECOMMENDATION for complex commands (globs, operators, etc):
117
+ // Move to package.json script and reference it:
118
+ // Bad: scanCommand: "npx secretlint **/*" (glob patterns rejected)
119
+ // Bad: scanCommand: "cmd1 && cmd2" (shell operators rejected)
120
+ // Good: scanCommand: "npm run scan:secrets"
121
+ // package.json: { "scan:secrets": "npx secretlint '**/*'" }
99
122
  const result = safeExecFromString(command, {
100
123
  encoding: 'utf8',
101
124
  stdio: 'pipe',
@@ -154,7 +177,7 @@ export function formatToolName(tool) {
154
177
  /**
155
178
  * Show performance warning if scan was slow
156
179
  */
157
- export function showPerformanceWarning(tool, duration, threshold) {
180
+ export function showPerformanceWarning(tool, duration, threshold, hasExplicitCommand = false) {
158
181
  if (duration <= threshold) {
159
182
  return;
160
183
  }
@@ -164,7 +187,12 @@ export function showPerformanceWarning(tool, duration, threshold) {
164
187
  console.warn(chalk.gray(' Consider installing gitleaks for faster scanning:'));
165
188
  console.warn(chalk.gray(' • macOS: brew install gitleaks'));
166
189
  console.warn(chalk.gray(' • Linux: See https://github.com/gitleaks/gitleaks#installation'));
167
- console.warn(chalk.gray(' • Or add explicit scanCommand in config\n'));
190
+ if (hasExplicitCommand) {
191
+ console.warn(chalk.gray(''));
192
+ }
193
+ else {
194
+ console.warn(chalk.gray(' • Or add explicit scanCommand in config\n'));
195
+ }
168
196
  }
169
197
  }
170
198
  /**