@vibecheckai/cli 2.5.1 → 2.5.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +88 -88
- package/dist/autopatch/verified-autopatch.js +10 -10
- package/dist/bundles/index.js +3 -3
- package/dist/bundles/vibecheck-core.js +25799 -0
- package/dist/bundles/vibecheck-security.js +208687 -0
- package/dist/bundles/vibecheck-ship.js +2318 -0
- package/dist/commands/baseline.js +1 -1
- package/dist/commands/cache.js +4 -4
- package/dist/commands/checkpoint.d.ts +1 -1
- package/dist/commands/checkpoint.js +1 -1
- package/dist/commands/doctor.d.ts +1 -1
- package/dist/commands/doctor.js +12 -12
- package/dist/commands/evidence.js +4 -4
- package/dist/commands/evidence.js.map +1 -1
- package/dist/commands/explain.d.ts +1 -1
- package/dist/commands/explain.js +4 -4
- package/dist/commands/fix-consolidated.d.ts +1 -1
- package/dist/commands/fix-consolidated.js +3 -3
- package/dist/commands/init.d.ts +1 -1
- package/dist/commands/init.js +7 -7
- package/dist/commands/launcher.d.ts +1 -1
- package/dist/commands/launcher.js +9 -9
- package/dist/commands/on.d.ts +1 -1
- package/dist/commands/on.js +2 -2
- package/dist/commands/replay.d.ts +1 -1
- package/dist/commands/replay.js +5 -5
- package/dist/commands/scan-consolidated.d.ts +1 -1
- package/dist/commands/scan-consolidated.js +10 -10
- package/dist/commands/scan-secrets.js +5 -5
- package/dist/commands/scan-vulnerabilities-enhanced.d.ts +1 -1
- package/dist/commands/scan-vulnerabilities-enhanced.js +1 -1
- package/dist/commands/scan-vulnerabilities-osv.d.ts +1 -1
- package/dist/commands/scan-vulnerabilities-osv.js +6 -6
- package/dist/commands/scan-vulnerabilities-osv.js.map +1 -1
- package/dist/commands/secrets-allowlist.js +5 -5
- package/dist/commands/secrets-allowlist.js.map +1 -1
- package/dist/commands/ship-consolidated.d.ts +1 -1
- package/dist/commands/ship-consolidated.js +198 -198
- package/dist/commands/stats.d.ts +1 -1
- package/dist/commands/stats.js +5 -5
- package/dist/commands/upgrade.d.ts +1 -1
- package/dist/commands/upgrade.js +2 -2
- package/dist/commands/upgrade.js.map +1 -1
- package/dist/fix/backup.js +1 -1
- package/dist/formatters/sarif-enhanced.js +3 -3
- package/dist/formatters/sarif-enhanced.js.map +1 -1
- package/dist/formatters/sarif-v2.js +17 -17
- package/dist/formatters/sarif-v2.js.map +1 -1
- package/dist/formatters/sarif.js +8 -8
- package/dist/formatters/sarif.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +102 -150
- package/dist/index.js.map +1 -1
- package/dist/init/ci-generator.js +29 -29
- package/dist/init/hooks-installer.js +19 -19
- package/dist/mcp/server.js +1 -1
- package/dist/mcp/telemetry.js +2 -2
- package/dist/reality/reality-runner.d.ts +1 -1
- package/dist/reality/reality-runner.js +3 -3
- package/dist/reality/receipt-generator.js +4 -4
- package/dist/runtime/client.js +5 -5
- package/dist/runtime/client.js.map +1 -1
- package/dist/runtime/creds.js +4 -4
- package/dist/runtime/creds.js.map +1 -1
- package/dist/runtime/json-output.js +1 -1
- package/dist/scan/reality-sniff.js +1 -1
- package/dist/truth-pack/index.js +1 -1
- package/dist/ui/frame.js +1 -1
- package/dist/ui.js +1 -1
- package/package.json +9 -11
package/dist/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
"use strict";
|
|
3
3
|
/**
|
|
4
|
-
*
|
|
4
|
+
* vibecheck CLI
|
|
5
5
|
*
|
|
6
6
|
* Command-line interface for local security scanning
|
|
7
7
|
*/
|
|
@@ -48,7 +48,7 @@ const fs_1 = require("fs");
|
|
|
48
48
|
const path_2 = require("path");
|
|
49
49
|
// Use package.json version instead of hardcoding
|
|
50
50
|
const { version: CLI_VERSION = '0.0.0' } = require('../package.json');
|
|
51
|
-
const
|
|
51
|
+
const vibecheck_security_1 = require('./bundles/vibecheck-security');
|
|
52
52
|
const creds_1 = require("./runtime/creds");
|
|
53
53
|
const client_1 = require("./runtime/client");
|
|
54
54
|
const exit_codes_1 = require("./runtime/exit-codes");
|
|
@@ -56,15 +56,10 @@ const json_output_1 = require("./runtime/json-output");
|
|
|
56
56
|
const semver_1 = require("./runtime/semver");
|
|
57
57
|
const scan_vulnerabilities_osv_1 = require("./commands/scan-vulnerabilities-osv");
|
|
58
58
|
const cache_1 = require("./commands/cache");
|
|
59
|
-
const init_1 = require("./commands/init");
|
|
60
|
-
const on_1 = require("./commands/on");
|
|
61
|
-
const stats_1 = require("./commands/stats");
|
|
62
|
-
const checkpoint_1 = require("./commands/checkpoint");
|
|
63
|
-
const upgrade_1 = require("./commands/upgrade");
|
|
64
59
|
const readline = __importStar(require("readline"));
|
|
65
60
|
const auth_utils_1 = require("./runtime/auth-utils");
|
|
66
61
|
const frame_1 = require("./ui/frame");
|
|
67
|
-
const
|
|
62
|
+
const init_1 = require("./init");
|
|
68
63
|
// ═══════════════════════════════════════════════════════════════════════════════
|
|
69
64
|
// ENTERPRISE CLI STYLING
|
|
70
65
|
// ═══════════════════════════════════════════════════════════════════════════════
|
|
@@ -73,7 +68,7 @@ const init_2 = require("./init");
|
|
|
73
68
|
// ═══════════════════════════════════════════════════════════════════════════════
|
|
74
69
|
// Detect Unicode support
|
|
75
70
|
const hasUnicode = () => {
|
|
76
|
-
if (process.env.
|
|
71
|
+
if (process.env.VIBECHECK_NO_UNICODE === '1')
|
|
77
72
|
return false;
|
|
78
73
|
if (process.platform === 'win32') {
|
|
79
74
|
return (process.env.CI ||
|
|
@@ -490,7 +485,7 @@ async function delay(ms) {
|
|
|
490
485
|
return new Promise(resolve => setTimeout(resolve, ms));
|
|
491
486
|
}
|
|
492
487
|
// Config file path for storing API key
|
|
493
|
-
const CONFIG_DIR = (0, path_2.join)(process.env.HOME || process.env.USERPROFILE || '.', '.
|
|
488
|
+
const CONFIG_DIR = (0, path_2.join)(process.env.HOME || process.env.USERPROFILE || '.', '.vibecheck');
|
|
494
489
|
const CONFIG_FILE = (0, path_2.join)(CONFIG_DIR, 'credentials.json');
|
|
495
490
|
function loadConfig() {
|
|
496
491
|
try {
|
|
@@ -511,7 +506,7 @@ function saveConfig(config) {
|
|
|
511
506
|
}
|
|
512
507
|
// Interactive menu helpers
|
|
513
508
|
function isInteractiveAllowed(argv) {
|
|
514
|
-
if (process.env.
|
|
509
|
+
if (process.env.VIBECHECK_NO_INTERACTIVE === '1')
|
|
515
510
|
return false;
|
|
516
511
|
if (argv.includes('--no-interactive'))
|
|
517
512
|
return false;
|
|
@@ -525,7 +520,7 @@ function nowStamp() {
|
|
|
525
520
|
return `${d.getFullYear()}${pad(d.getMonth() + 1)}${pad(d.getDate())}-${pad(d.getHours())}${pad(d.getMinutes())}${pad(d.getSeconds())}`;
|
|
526
521
|
}
|
|
527
522
|
function defaultReportPath(projectPath, kind, ext) {
|
|
528
|
-
const dir = (0, path_2.join)(projectPath, '.
|
|
523
|
+
const dir = (0, path_2.join)(projectPath, '.vibecheck', 'reports');
|
|
529
524
|
if (!(0, fs_1.existsSync)(dir))
|
|
530
525
|
(0, fs_1.mkdirSync)(dir, { recursive: true });
|
|
531
526
|
return (0, path_2.join)(dir, `${kind}-${nowStamp()}.${ext}`);
|
|
@@ -543,8 +538,8 @@ async function requireAuthAsync(requiredTier) {
|
|
|
543
538
|
cachedAuthState = state;
|
|
544
539
|
if (!state.apiKey && !state.accessToken) {
|
|
545
540
|
console.error(`\n${c.critical('ERROR')} Authentication required\n`);
|
|
546
|
-
console.log(` ${c.dim('Run')} ${c.bold('
|
|
547
|
-
console.log(` ${c.dim('Get your API key from')} ${c.info('https://
|
|
541
|
+
console.log(` ${c.dim('Run')} ${c.bold('vibecheck auth --key YOUR_API_KEY')} ${c.dim('to authenticate')}`);
|
|
542
|
+
console.log(` ${c.dim('Get your API key from')} ${c.info('https://vibecheckai.dev/api-key')}\n`);
|
|
548
543
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.AUTH_FAILURE);
|
|
549
544
|
}
|
|
550
545
|
// Check if cached entitlements are still valid
|
|
@@ -586,7 +581,7 @@ function checkTierAccess(state, requiredTier) {
|
|
|
586
581
|
if (currentLevel < requiredLevel) {
|
|
587
582
|
console.error(`\n${c.critical('UPGRADE REQUIRED')} This feature requires ${c.bold(requiredTier.toUpperCase())} tier\n`);
|
|
588
583
|
console.log(` ${c.dim('Current tier:')} ${c.info(state.tier || 'free')}`);
|
|
589
|
-
console.log(` ${c.dim('Upgrade at')} ${c.info('https://
|
|
584
|
+
console.log(` ${c.dim('Upgrade at')} ${c.info('https://vibecheckai.dev/pricing')}\n`);
|
|
590
585
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.AUTH_FAILURE);
|
|
591
586
|
}
|
|
592
587
|
return state;
|
|
@@ -596,8 +591,8 @@ function requireAuth(tier) {
|
|
|
596
591
|
const config = loadConfig();
|
|
597
592
|
if (!config.apiKey) {
|
|
598
593
|
console.error(`\n${c.critical('ERROR')} Authentication required\n`);
|
|
599
|
-
console.log(` ${c.dim('Run')} ${c.bold('
|
|
600
|
-
console.log(` ${c.dim('Get your API key from')} ${c.info('https://
|
|
594
|
+
console.log(` ${c.dim('Run')} ${c.bold('vibecheck auth --key YOUR_API_KEY')} ${c.dim('to authenticate')}`);
|
|
595
|
+
console.log(` ${c.dim('Get your API key from')} ${c.info('https://vibecheckai.dev/api-key')}\n`);
|
|
601
596
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.AUTH_FAILURE);
|
|
602
597
|
}
|
|
603
598
|
if (tier) {
|
|
@@ -607,21 +602,21 @@ function requireAuth(tier) {
|
|
|
607
602
|
if (currentLevel < requiredLevel) {
|
|
608
603
|
console.error(`\n${c.critical('UPGRADE REQUIRED')} This feature requires ${c.bold(tier.toUpperCase())} tier\n`);
|
|
609
604
|
console.log(` ${c.dim('Current tier:')} ${c.info(config.tier || 'free')}`);
|
|
610
|
-
console.log(` ${c.dim('Upgrade at')} ${c.info('https://
|
|
605
|
+
console.log(` ${c.dim('Upgrade at')} ${c.info('https://vibecheckai.dev/pricing')}\n`);
|
|
611
606
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.AUTH_FAILURE);
|
|
612
607
|
}
|
|
613
608
|
}
|
|
614
609
|
return config;
|
|
615
610
|
}
|
|
616
611
|
program
|
|
617
|
-
.name('
|
|
618
|
-
.description('
|
|
612
|
+
.name('vibecheck')
|
|
613
|
+
.description('vibecheck AI - Security scanning for your codebase')
|
|
619
614
|
.version(CLI_VERSION);
|
|
620
615
|
// Login command
|
|
621
616
|
program
|
|
622
617
|
.command('login')
|
|
623
|
-
.description('Login with your
|
|
624
|
-
.option('-k, --key <apiKey>', 'Your API key from
|
|
618
|
+
.description('Login with your vibecheck API key')
|
|
619
|
+
.option('-k, --key <apiKey>', 'Your API key from vibecheckai.dev')
|
|
625
620
|
.action(async (options) => {
|
|
626
621
|
printLogo();
|
|
627
622
|
// Use existing auth logic
|
|
@@ -667,8 +662,8 @@ program
|
|
|
667
662
|
// Auth command (keep for backward compatibility)
|
|
668
663
|
program
|
|
669
664
|
.command('auth')
|
|
670
|
-
.description('Authenticate with your
|
|
671
|
-
.option('-k, --key <apiKey>', 'Your API key from
|
|
665
|
+
.description('Authenticate with your vibecheck API key')
|
|
666
|
+
.option('-k, --key <apiKey>', 'Your API key from vibecheckai.dev')
|
|
672
667
|
.option('--logout', 'Remove stored credentials')
|
|
673
668
|
.option('--status', 'Check authentication status')
|
|
674
669
|
.option('--refresh', 'Force revalidation of cached entitlements')
|
|
@@ -735,7 +730,7 @@ program
|
|
|
735
730
|
const hours = (0, auth_utils_1.hoursUntilExpiry)(state.expiresAt);
|
|
736
731
|
console.log('');
|
|
737
732
|
console.log(` ${styles.brightYellow}${icons.warning}${styles.reset} ${styles.bold}Entitlements expiring in ${hours}h${styles.reset}`);
|
|
738
|
-
console.log(` ${styles.dim}Run${styles.reset} ${styles.brightCyan}
|
|
733
|
+
console.log(` ${styles.dim}Run${styles.reset} ${styles.brightCyan}vibecheck auth --refresh${styles.reset} ${styles.dim}to revalidate${styles.reset}`);
|
|
739
734
|
}
|
|
740
735
|
}
|
|
741
736
|
else {
|
|
@@ -743,10 +738,10 @@ program
|
|
|
743
738
|
`${styles.brightRed}${styles.bold}${icons.error} NOT AUTHENTICATED${styles.reset}`,
|
|
744
739
|
'',
|
|
745
740
|
`${styles.dim}To authenticate, run:${styles.reset}`,
|
|
746
|
-
`${styles.brightCyan}
|
|
741
|
+
`${styles.brightCyan}vibecheck auth --key YOUR_API_KEY${styles.reset}`,
|
|
747
742
|
'',
|
|
748
743
|
`${styles.dim}Get your API key from:${styles.reset}`,
|
|
749
|
-
`${styles.brightBlue}https://
|
|
744
|
+
`${styles.brightBlue}https://vibecheckai.dev/api-key${styles.reset}`,
|
|
750
745
|
];
|
|
751
746
|
const framed = frameLines(statusLines, { padding: 2 });
|
|
752
747
|
console.log(framed.join('\n'));
|
|
@@ -763,7 +758,7 @@ program
|
|
|
763
758
|
`${styles.brightRed}${styles.bold}${icons.error} NO CREDENTIALS FOUND${styles.reset}`,
|
|
764
759
|
'',
|
|
765
760
|
`${styles.dim}Authenticate first with:${styles.reset}`,
|
|
766
|
-
`${styles.brightCyan}
|
|
761
|
+
`${styles.brightCyan}vibecheck auth --key YOUR_API_KEY${styles.reset}`,
|
|
767
762
|
];
|
|
768
763
|
console.log(frameLines(errorLines, { padding: 2 }).join('\n'));
|
|
769
764
|
console.log('');
|
|
@@ -820,10 +815,10 @@ program
|
|
|
820
815
|
`${styles.brightCyan}${styles.bold}${icons.auth} AUTHENTICATION${styles.reset}`,
|
|
821
816
|
'',
|
|
822
817
|
`${styles.dim}To authenticate, run:${styles.reset}`,
|
|
823
|
-
`${styles.bold}
|
|
818
|
+
`${styles.bold}vibecheck auth --key YOUR_API_KEY${styles.reset}`,
|
|
824
819
|
'',
|
|
825
820
|
`${styles.dim}Get your API key from:${styles.reset}`,
|
|
826
|
-
`${styles.brightBlue}https://
|
|
821
|
+
`${styles.brightBlue}https://vibecheckai.dev/api-key${styles.reset}`,
|
|
827
822
|
'',
|
|
828
823
|
`${styles.dim}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${styles.reset}`,
|
|
829
824
|
'',
|
|
@@ -859,7 +854,7 @@ program
|
|
|
859
854
|
}
|
|
860
855
|
// Real API validation
|
|
861
856
|
console.log('');
|
|
862
|
-
const s = spinner('Validating API key with
|
|
857
|
+
const s = spinner('Validating API key with vibecheck API...');
|
|
863
858
|
const result = await (0, client_1.validateApiKey)({ apiKey: options.key });
|
|
864
859
|
if (!result.ok) {
|
|
865
860
|
s.stop(false, 'Validation failed');
|
|
@@ -875,7 +870,7 @@ program
|
|
|
875
870
|
` ${styles.dim}${icons.bullet}${styles.reset} Network connectivity issues`,
|
|
876
871
|
'',
|
|
877
872
|
`${styles.dim}Get a new API key from:${styles.reset}`,
|
|
878
|
-
`${styles.brightBlue}https://
|
|
873
|
+
`${styles.brightBlue}https://vibecheckai.dev/api-key${styles.reset}`,
|
|
879
874
|
];
|
|
880
875
|
console.log(frameLines(errorLines, { padding: 2 }).join('\n'));
|
|
881
876
|
console.log('');
|
|
@@ -1200,7 +1195,7 @@ program
|
|
|
1200
1195
|
});
|
|
1201
1196
|
try {
|
|
1202
1197
|
// Import the code smell predictor from core package
|
|
1203
|
-
const { codeSmellPredictor } = require('./bundles/
|
|
1198
|
+
const { codeSmellPredictor } = require('./bundles/vibecheck-core');
|
|
1204
1199
|
const report = await codeSmellPredictor.predict(projectPath);
|
|
1205
1200
|
// Filter by severity
|
|
1206
1201
|
let filteredSmells = report.smells;
|
|
@@ -1459,7 +1454,7 @@ program
|
|
|
1459
1454
|
failedFixes: applyResult.failedFixes,
|
|
1460
1455
|
errors: applyResult.errors,
|
|
1461
1456
|
verification: verifyResult,
|
|
1462
|
-
rollbackCommand: `
|
|
1457
|
+
rollbackCommand: `vibecheck fix rollback --run ${runId}`,
|
|
1463
1458
|
}, null, 2));
|
|
1464
1459
|
}
|
|
1465
1460
|
else {
|
|
@@ -1489,7 +1484,7 @@ program
|
|
|
1489
1484
|
console.log('');
|
|
1490
1485
|
}
|
|
1491
1486
|
console.log(` ${styles.dim}Backup ID:${styles.reset} ${styles.bold}${runId}${styles.reset}`);
|
|
1492
|
-
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}
|
|
1487
|
+
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}vibecheck fix rollback --run ${runId}${styles.reset}`);
|
|
1493
1488
|
console.log('');
|
|
1494
1489
|
}
|
|
1495
1490
|
}
|
|
@@ -1555,7 +1550,7 @@ program
|
|
|
1555
1550
|
console.log(` ${styles.dim}Size:${styles.reset} ${sizeKB} KB`);
|
|
1556
1551
|
console.log('');
|
|
1557
1552
|
}
|
|
1558
|
-
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}
|
|
1553
|
+
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}vibecheck fix rollback --run <runId>${styles.reset}`);
|
|
1559
1554
|
console.log('');
|
|
1560
1555
|
}
|
|
1561
1556
|
}
|
|
@@ -1587,8 +1582,8 @@ program
|
|
|
1587
1582
|
else {
|
|
1588
1583
|
console.log('');
|
|
1589
1584
|
console.log(` ${styles.brightRed}${icons.error}${styles.reset} ${styles.bold}Run ID required${styles.reset}`);
|
|
1590
|
-
console.log(` ${styles.dim}Use:${styles.reset} ${styles.bold}
|
|
1591
|
-
console.log(` ${styles.dim}List backups:${styles.reset} ${styles.bold}
|
|
1585
|
+
console.log(` ${styles.dim}Use:${styles.reset} ${styles.bold}vibecheck fix rollback --run <runId>${styles.reset}`);
|
|
1586
|
+
console.log(` ${styles.dim}List backups:${styles.reset} ${styles.bold}vibecheck fix rollback --list${styles.reset}`);
|
|
1592
1587
|
console.log('');
|
|
1593
1588
|
}
|
|
1594
1589
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.USER_ERROR, 'Run ID required');
|
|
@@ -1692,8 +1687,8 @@ program
|
|
|
1692
1687
|
});
|
|
1693
1688
|
try {
|
|
1694
1689
|
// Import ship functionality
|
|
1695
|
-
const { shipBadgeGenerator } = require('./bundles/
|
|
1696
|
-
const { importGraphScanner } = require('./bundles/
|
|
1690
|
+
const { shipBadgeGenerator } = require('./bundles/vibecheck-ship');
|
|
1691
|
+
const { importGraphScanner } = require('./bundles/vibecheck-ship');
|
|
1697
1692
|
// Run ship check
|
|
1698
1693
|
const shipResult = await shipBadgeGenerator.generateShipBadge({
|
|
1699
1694
|
projectPath,
|
|
@@ -1829,7 +1824,7 @@ program
|
|
|
1829
1824
|
});
|
|
1830
1825
|
try {
|
|
1831
1826
|
// Import pro ship scanner
|
|
1832
|
-
const { ProShipScanner } = require('./bundles/
|
|
1827
|
+
const { ProShipScanner } = require('./bundles/vibecheck-ship');
|
|
1833
1828
|
const proShipScanner = new ProShipScanner();
|
|
1834
1829
|
const scanConfig = {
|
|
1835
1830
|
projectPath,
|
|
@@ -1964,7 +1959,7 @@ program
|
|
|
1964
1959
|
console.log('');
|
|
1965
1960
|
try {
|
|
1966
1961
|
// Import reality functionality
|
|
1967
|
-
const { realityScanner } = require('./bundles/
|
|
1962
|
+
const { realityScanner } = require('./bundles/vibecheck-ship');
|
|
1968
1963
|
const { checkPlaywrightDependencies, runPlaywrightTests, runPlaywrightCodegen, createArtifactDirectory, copyTestToArtifacts, formatDuration } = require('./reality/reality-runner');
|
|
1969
1964
|
const { runStaticScan, formatStaticScanResults, generateButtonSweepTest, } = require('./reality/no-dead-buttons');
|
|
1970
1965
|
const { spawn } = require('child_process');
|
|
@@ -2044,7 +2039,7 @@ program
|
|
|
2044
2039
|
console.log(` ${styles.dim}Artifacts:${styles.reset} ${truncatePath(artifacts.artifactDir)}`);
|
|
2045
2040
|
console.log('');
|
|
2046
2041
|
console.log(` ${styles.bold}To run the recorded test:${styles.reset}`);
|
|
2047
|
-
console.log(` ${styles.brightCyan}
|
|
2042
|
+
console.log(` ${styles.brightCyan}vibecheck reality --run --flow ${options.flow}${styles.reset}`);
|
|
2048
2043
|
console.log('');
|
|
2049
2044
|
process.exit(0);
|
|
2050
2045
|
}
|
|
@@ -2096,7 +2091,7 @@ program
|
|
|
2096
2091
|
requireDataActionId: false,
|
|
2097
2092
|
};
|
|
2098
2093
|
const buttonSweepTest = generateButtonSweepTest(buttonSweepConfig);
|
|
2099
|
-
const buttonSweepOutputDir = (0, path_2.join)(process.cwd(), '.
|
|
2094
|
+
const buttonSweepOutputDir = (0, path_2.join)(process.cwd(), '.vibecheck', 'reality-tests');
|
|
2100
2095
|
if (!(0, fs_1.existsSync)(buttonSweepOutputDir)) {
|
|
2101
2096
|
(0, fs_1.mkdirSync)(buttonSweepOutputDir, { recursive: true });
|
|
2102
2097
|
}
|
|
@@ -2151,7 +2146,7 @@ program
|
|
|
2151
2146
|
}
|
|
2152
2147
|
}
|
|
2153
2148
|
// Generate Playwright test for reality mode
|
|
2154
|
-
const outputDir = (0, path_2.join)(process.cwd(), '.
|
|
2149
|
+
const outputDir = (0, path_2.join)(process.cwd(), '.vibecheck', 'reality-tests');
|
|
2155
2150
|
if (!(0, fs_1.existsSync)(outputDir)) {
|
|
2156
2151
|
(0, fs_1.mkdirSync)(outputDir, { recursive: true });
|
|
2157
2152
|
}
|
|
@@ -2339,7 +2334,7 @@ program
|
|
|
2339
2334
|
console.log(` ${styles.bold}HOW TO RUN${styles.reset}`);
|
|
2340
2335
|
printDivider();
|
|
2341
2336
|
console.log(` ${styles.dim}Option 1: Use --run flag (recommended):${styles.reset}`);
|
|
2342
|
-
console.log(` ${styles.brightCyan}
|
|
2337
|
+
console.log(` ${styles.brightCyan}vibecheck reality --run -f ${options.flow}${styles.reset}`);
|
|
2343
2338
|
console.log('');
|
|
2344
2339
|
console.log(` ${styles.dim}Option 2: Run manually:${styles.reset}`);
|
|
2345
2340
|
console.log(` ${styles.brightCyan}cd ${outputDir}${styles.reset}`);
|
|
@@ -2348,7 +2343,7 @@ program
|
|
|
2348
2343
|
console.log(` ${styles.bold}WHERE ARTIFACTS ARE SAVED${styles.reset}`);
|
|
2349
2344
|
printDivider();
|
|
2350
2345
|
console.log(` ${styles.dim}When using --run, artifacts are stored under:${styles.reset}`);
|
|
2351
|
-
console.log(` ${styles.brightCyan}.
|
|
2346
|
+
console.log(` ${styles.brightCyan}.vibecheck/reality/<runId>/${styles.reset}`);
|
|
2352
2347
|
console.log('');
|
|
2353
2348
|
console.log(` ${styles.dim}Contents:${styles.reset}`);
|
|
2354
2349
|
console.log(` ${styles.bullet} ${styles.bold}reality-*.test.ts${styles.reset} - Generated test file`);
|
|
@@ -2425,7 +2420,7 @@ program
|
|
|
2425
2420
|
let graphBuilder;
|
|
2426
2421
|
if (options.receipt) {
|
|
2427
2422
|
// Load graph from receipt
|
|
2428
|
-
const receiptPath = join(projectPath, '.
|
|
2423
|
+
const receiptPath = join(projectPath, '.vibecheck', 'receipts', options.receipt, 'reality-graph.json');
|
|
2429
2424
|
if (!existsSync(receiptPath)) {
|
|
2430
2425
|
console.log(` ${styles.brightRed}${icons.error}${styles.reset} Receipt graph not found`);
|
|
2431
2426
|
process.exit(1);
|
|
@@ -2486,7 +2481,7 @@ program
|
|
|
2486
2481
|
}
|
|
2487
2482
|
// Export graph
|
|
2488
2483
|
if (options.export) {
|
|
2489
|
-
const outputPath = join(projectPath, '.
|
|
2484
|
+
const outputPath = join(projectPath, '.vibecheck', 'reality-graph.json');
|
|
2490
2485
|
writeFileSync(outputPath, graphBuilder.export());
|
|
2491
2486
|
console.log(` ${styles.brightGreen}✓${styles.reset} Graph exported to ${outputPath}`);
|
|
2492
2487
|
console.log('');
|
|
@@ -2522,7 +2517,7 @@ program
|
|
|
2522
2517
|
console.log(` ${styles.brightRed}${icons.error}${styles.reset} Missing required options: --file, --line, --patch`);
|
|
2523
2518
|
console.log('');
|
|
2524
2519
|
console.log(` ${styles.bold}Usage:${styles.reset}`);
|
|
2525
|
-
console.log(`
|
|
2520
|
+
console.log(` vibecheck autopatch:verify --file src/app.ts --line 42 --patch "const apiUrl = process.env.API_URL;"`);
|
|
2526
2521
|
console.log('');
|
|
2527
2522
|
process.exit(1);
|
|
2528
2523
|
}
|
|
@@ -2572,7 +2567,7 @@ program
|
|
|
2572
2567
|
}
|
|
2573
2568
|
else {
|
|
2574
2569
|
console.log(` ${styles.bold}To merge this fix:${styles.reset}`);
|
|
2575
|
-
console.log(` ${styles.brightCyan}
|
|
2570
|
+
console.log(` ${styles.brightCyan}vibecheck autopatch:merge --fix-id ${fix.id}${styles.reset}`);
|
|
2576
2571
|
console.log('');
|
|
2577
2572
|
}
|
|
2578
2573
|
}
|
|
@@ -2637,7 +2632,7 @@ program
|
|
|
2637
2632
|
program
|
|
2638
2633
|
.command('receipt:verify')
|
|
2639
2634
|
.description('Verify Proof-of-Execution Receipt')
|
|
2640
|
-
.option('-p, --path <path>', 'Receipt path or directory', '.
|
|
2635
|
+
.option('-p, --path <path>', 'Receipt path or directory', '.vibecheck/receipts')
|
|
2641
2636
|
.option('--org-public-key <key>', 'Organization public key for verification (PEM format)')
|
|
2642
2637
|
.action(async (options) => {
|
|
2643
2638
|
printLogo();
|
|
@@ -2739,7 +2734,7 @@ program
|
|
|
2739
2734
|
'Autopilot requires Pro tier or higher.',
|
|
2740
2735
|
'',
|
|
2741
2736
|
`${styles.dim}Current tier:${styles.reset} ${config.tier || 'free'}`,
|
|
2742
|
-
`${styles.dim}Upgrade at:${styles.reset} ${styles.brightBlue}https://
|
|
2737
|
+
`${styles.dim}Upgrade at:${styles.reset} ${styles.brightBlue}https://vibecheckai.dev/pricing${styles.reset}`,
|
|
2743
2738
|
];
|
|
2744
2739
|
console.log(frameLines(errorLines, { padding: 2 }).join('\n'));
|
|
2745
2740
|
console.log('');
|
|
@@ -2755,7 +2750,7 @@ program
|
|
|
2755
2750
|
'',
|
|
2756
2751
|
'Rollback mode requires --run <runId>',
|
|
2757
2752
|
'',
|
|
2758
|
-
`${styles.dim}Example:${styles.reset}
|
|
2753
|
+
`${styles.dim}Example:${styles.reset} vibecheck autopilot rollback --run abc123def456`,
|
|
2759
2754
|
];
|
|
2760
2755
|
console.log(frameLines(errorLines, { padding: 2 }).join('\n'));
|
|
2761
2756
|
console.log('');
|
|
@@ -2777,7 +2772,7 @@ program
|
|
|
2777
2772
|
const s = spinner(`Running autopilot ${autopilotMode}...`);
|
|
2778
2773
|
try {
|
|
2779
2774
|
// Dynamic import to avoid bundling issues
|
|
2780
|
-
const { runAutopilot } = await Promise.resolve().then(() => __importStar(require('./bundles/
|
|
2775
|
+
const { runAutopilot } = await Promise.resolve().then(() => __importStar(require('./bundles/vibecheck-core')));
|
|
2781
2776
|
const projectName = (0, path_1.basename)(projectPath);
|
|
2782
2777
|
const result = await runAutopilot({
|
|
2783
2778
|
projectPath,
|
|
@@ -2822,7 +2817,7 @@ program
|
|
|
2822
2817
|
console.log(` ${styles.dim}Files:${styles.reset} ${pack.impactedFiles.slice(0, 3).join(', ')}${pack.impactedFiles.length > 3 ? '...' : ''}`);
|
|
2823
2818
|
console.log('');
|
|
2824
2819
|
}
|
|
2825
|
-
console.log(` ${styles.dim}Run${styles.reset} ${styles.bold}
|
|
2820
|
+
console.log(` ${styles.dim}Run${styles.reset} ${styles.bold}vibecheck autopilot apply${styles.reset} ${styles.dim}to apply these fixes${styles.reset}`);
|
|
2826
2821
|
console.log('');
|
|
2827
2822
|
}
|
|
2828
2823
|
else if (result.mode === 'rollback') {
|
|
@@ -2872,7 +2867,7 @@ program
|
|
|
2872
2867
|
console.log(` ${styles.dim}Total duration:${styles.reset} ${result.duration}ms`);
|
|
2873
2868
|
if (result.runId) {
|
|
2874
2869
|
console.log('');
|
|
2875
|
-
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}
|
|
2870
|
+
console.log(` ${styles.dim}To rollback:${styles.reset} ${styles.bold}vibecheck autopilot rollback --run ${result.runId}${styles.reset}`);
|
|
2876
2871
|
}
|
|
2877
2872
|
console.log('');
|
|
2878
2873
|
}
|
|
@@ -2885,33 +2880,7 @@ program
|
|
|
2885
2880
|
(0, exit_codes_1.exitWith)(exit_codes_1.ExitCode.SYSTEM_ERROR, 'Autopilot execution failed');
|
|
2886
2881
|
}
|
|
2887
2882
|
});
|
|
2888
|
-
// Init command
|
|
2889
|
-
program
|
|
2890
|
-
.command('init')
|
|
2891
|
-
.description('Initialize Guardrail in a project with framework detection and templates')
|
|
2892
|
-
.option('-p, --path <path>', 'Project path', '.')
|
|
2893
|
-
.option('-t, --template <template>', 'Template: startup, enterprise, or oss')
|
|
2894
|
-
.option('--ci', 'Set up CI/CD integration', false)
|
|
2895
|
-
.option('--hooks', 'Set up pre-commit hooks', false)
|
|
2896
|
-
.option('--hook-runner <runner>', 'Hook runner: husky or lefthook')
|
|
2897
|
-
.option('--no-interactive', 'Disable interactive prompts')
|
|
2898
|
-
.action(async (options) => {
|
|
2899
|
-
printLogo();
|
|
2900
|
-
console.log('');
|
|
2901
|
-
const projectPath = (0, path_1.resolve)(options.path);
|
|
2902
|
-
const projectName = (0, path_1.basename)(projectPath);
|
|
2903
|
-
const headerLines = [
|
|
2904
|
-
`${styles.brightCyan}${styles.bold}${icons.ship} INITIALIZING GUARDRAIL${styles.reset}`,
|
|
2905
|
-
'',
|
|
2906
|
-
`${styles.dim}Project:${styles.reset} ${styles.bold}${projectName}${styles.reset}`,
|
|
2907
|
-
`${styles.dim}Path:${styles.reset} ${truncatePath(projectPath)}`,
|
|
2908
|
-
`${styles.dim}Time:${styles.reset} ${new Date().toLocaleString()}`,
|
|
2909
|
-
];
|
|
2910
|
-
const framed = frameLines(headerLines, { padding: 2 });
|
|
2911
|
-
console.log(framed.join('\n'));
|
|
2912
|
-
console.log('');
|
|
2913
|
-
await initProject(projectPath, options);
|
|
2914
|
-
});
|
|
2883
|
+
// Init command is registered via registerInitCommand() below
|
|
2915
2884
|
// Helper functions with realistic output
|
|
2916
2885
|
async function runScan(projectPath, options) {
|
|
2917
2886
|
const s1 = spinner('Analyzing project structure...');
|
|
@@ -2977,7 +2946,7 @@ function countFiles(dir) {
|
|
|
2977
2946
|
}
|
|
2978
2947
|
async function generateFindings(projectPath) {
|
|
2979
2948
|
const findings = [];
|
|
2980
|
-
const guardian = new
|
|
2949
|
+
const guardian = new vibecheck_security_1.SecretsGuardian();
|
|
2981
2950
|
// File extensions to scan for secrets
|
|
2982
2951
|
const scanExtensions = ['.ts', '.js', '.tsx', '.jsx', '.json', '.env', '.yaml', '.yml', '.toml', '.py', '.rb'];
|
|
2983
2952
|
// Recursively get files to scan
|
|
@@ -3074,7 +3043,7 @@ async function generateFindings(projectPath) {
|
|
|
3074
3043
|
}
|
|
3075
3044
|
async function scanSecrets(projectPath, options) {
|
|
3076
3045
|
const s = spinner('Scanning for hardcoded secrets...');
|
|
3077
|
-
const guardian = new
|
|
3046
|
+
const guardian = new vibecheck_security_1.SecretsGuardian();
|
|
3078
3047
|
// Use enterprise-grade scanProject instead of custom file walking
|
|
3079
3048
|
// Handles: ignores, binary files, size caps, concurrency, dedupe
|
|
3080
3049
|
const report = await guardian.scanProject(projectPath, 'cli-scan', {
|
|
@@ -3250,7 +3219,7 @@ async function scanCompliance(projectPath, options) {
|
|
|
3250
3219
|
}
|
|
3251
3220
|
async function generateSBOM(projectPath, options) {
|
|
3252
3221
|
const s = spinner('Generating Software Bill of Materials...');
|
|
3253
|
-
const sbomGenerator = new
|
|
3222
|
+
const sbomGenerator = new vibecheck_security_1.SBOMGenerator();
|
|
3254
3223
|
try {
|
|
3255
3224
|
const sbom = await sbomGenerator.generate(projectPath, {
|
|
3256
3225
|
format: options.format || 'cyclonedx',
|
|
@@ -3313,7 +3282,7 @@ async function generateSBOM(projectPath, options) {
|
|
|
3313
3282
|
licenseSummary: [],
|
|
3314
3283
|
metadata: {
|
|
3315
3284
|
timestamp: new Date().toISOString(),
|
|
3316
|
-
tools: [{ vendor: '
|
|
3285
|
+
tools: [{ vendor: 'vibecheck', name: 'CLI', version: '1.0.0' }],
|
|
3317
3286
|
},
|
|
3318
3287
|
};
|
|
3319
3288
|
}
|
|
@@ -3326,7 +3295,7 @@ async function generateSBOM(projectPath, options) {
|
|
|
3326
3295
|
}
|
|
3327
3296
|
async function generateContainerSBOM(imageName, options) {
|
|
3328
3297
|
const s = spinner('Generating container SBOM...');
|
|
3329
|
-
const sbomGenerator = new
|
|
3298
|
+
const sbomGenerator = new vibecheck_security_1.SBOMGenerator();
|
|
3330
3299
|
try {
|
|
3331
3300
|
const sbom = await sbomGenerator.generateContainerSBOM(imageName, {
|
|
3332
3301
|
format: options.format || 'cyclonedx',
|
|
@@ -3614,19 +3583,19 @@ function outputResultsEnterprise(results, options) {
|
|
|
3614
3583
|
}
|
|
3615
3584
|
}
|
|
3616
3585
|
async function initProject(projectPath, options) {
|
|
3617
|
-
const configDir = (0, path_2.join)(projectPath, '.
|
|
3586
|
+
const configDir = (0, path_2.join)(projectPath, '.vibecheck');
|
|
3618
3587
|
const isTTY = process.stdin.isTTY && process.stdout.isTTY && options.interactive !== false;
|
|
3619
3588
|
// Step 1: Framework Detection
|
|
3620
3589
|
const s1 = spinner('Detecting project framework...');
|
|
3621
3590
|
await delay(300);
|
|
3622
|
-
const frameworkResult = (0,
|
|
3623
|
-
s1.stop(true, `Detected: ${(0,
|
|
3591
|
+
const frameworkResult = (0, init_1.detectFramework)(projectPath);
|
|
3592
|
+
s1.stop(true, `Detected: ${(0, init_1.formatFrameworkName)(frameworkResult.framework)}`);
|
|
3624
3593
|
// Display framework detection results
|
|
3625
3594
|
console.log('');
|
|
3626
3595
|
const frameworkLines = [
|
|
3627
3596
|
`${styles.brightBlue}${styles.bold}📦 FRAMEWORK DETECTION${styles.reset}`,
|
|
3628
3597
|
'',
|
|
3629
|
-
`${styles.dim}Framework:${styles.reset} ${styles.bold}${(0,
|
|
3598
|
+
`${styles.dim}Framework:${styles.reset} ${styles.bold}${(0, init_1.formatFrameworkName)(frameworkResult.framework)}${styles.reset}`,
|
|
3630
3599
|
`${styles.dim}Confidence:${styles.reset} ${frameworkResult.confidence}`,
|
|
3631
3600
|
'',
|
|
3632
3601
|
`${styles.dim}Signals:${styles.reset}`,
|
|
@@ -3649,7 +3618,7 @@ async function initProject(projectPath, options) {
|
|
|
3649
3618
|
}
|
|
3650
3619
|
}
|
|
3651
3620
|
else if (isTTY) {
|
|
3652
|
-
const templateChoices = (0,
|
|
3621
|
+
const templateChoices = (0, init_1.getTemplateChoices)();
|
|
3653
3622
|
templateType = await promptSelect('Select a configuration template', [
|
|
3654
3623
|
{
|
|
3655
3624
|
name: `${styles.brightGreen}Startup${styles.reset} - ${templateChoices[0].description}`,
|
|
@@ -3670,8 +3639,8 @@ async function initProject(projectPath, options) {
|
|
|
3670
3639
|
}
|
|
3671
3640
|
const s2 = spinner(`Applying ${templateType} template...`);
|
|
3672
3641
|
await delay(300);
|
|
3673
|
-
const template = (0,
|
|
3674
|
-
let config = (0,
|
|
3642
|
+
const template = (0, init_1.getTemplate)(templateType);
|
|
3643
|
+
let config = (0, init_1.mergeWithFrameworkDefaults)(template.config, frameworkResult.framework, frameworkResult.recommendedScans);
|
|
3675
3644
|
s2.stop(true, `Template: ${template.name}`);
|
|
3676
3645
|
// Step 3: Create configuration directory and write config
|
|
3677
3646
|
const s3 = spinner('Creating configuration...');
|
|
@@ -3680,7 +3649,7 @@ async function initProject(projectPath, options) {
|
|
|
3680
3649
|
(0, fs_1.mkdirSync)(configDir, { recursive: true });
|
|
3681
3650
|
}
|
|
3682
3651
|
// Validate config before writing
|
|
3683
|
-
const validation = (0,
|
|
3652
|
+
const validation = (0, init_1.validateConfig)(config);
|
|
3684
3653
|
if (!validation.success) {
|
|
3685
3654
|
s3.stop(false, 'Configuration validation failed');
|
|
3686
3655
|
console.log(` ${styles.brightRed}${icons.error}${styles.reset} Config validation errors:`);
|
|
@@ -3707,8 +3676,8 @@ async function initProject(projectPath, options) {
|
|
|
3707
3676
|
if (options.ci) {
|
|
3708
3677
|
const s4 = spinner('Setting up CI/CD integration...');
|
|
3709
3678
|
await delay(300);
|
|
3710
|
-
const ciProvider = (0,
|
|
3711
|
-
const ciGenResult = (0,
|
|
3679
|
+
const ciProvider = (0, init_1.getCIProviderFromProject)(projectPath) || 'github';
|
|
3680
|
+
const ciGenResult = (0, init_1.generateCIWorkflow)({
|
|
3712
3681
|
projectPath,
|
|
3713
3682
|
config,
|
|
3714
3683
|
provider: ciProvider,
|
|
@@ -3721,8 +3690,8 @@ async function initProject(projectPath, options) {
|
|
|
3721
3690
|
if (options.hooks) {
|
|
3722
3691
|
const s5 = spinner('Installing git hooks...');
|
|
3723
3692
|
await delay(300);
|
|
3724
|
-
const hookRunner = options.hookRunner || (0,
|
|
3725
|
-
const hookInstallResult = (0,
|
|
3693
|
+
const hookRunner = options.hookRunner || (0, init_1.getRecommendedRunner)(projectPath);
|
|
3694
|
+
const hookInstallResult = (0, init_1.installHooks)({
|
|
3726
3695
|
projectPath,
|
|
3727
3696
|
config,
|
|
3728
3697
|
runner: hookRunner,
|
|
@@ -3737,7 +3706,7 @@ async function initProject(projectPath, options) {
|
|
|
3737
3706
|
const successLines = [
|
|
3738
3707
|
`${styles.brightGreen}${styles.bold}${icons.success} INITIALIZATION COMPLETE${styles.reset}`,
|
|
3739
3708
|
'',
|
|
3740
|
-
`${styles.dim}Framework:${styles.reset} ${styles.bold}${(0,
|
|
3709
|
+
`${styles.dim}Framework:${styles.reset} ${styles.bold}${(0, init_1.formatFrameworkName)(frameworkResult.framework)}${styles.reset}`,
|
|
3741
3710
|
`${styles.dim}Template:${styles.reset} ${styles.bold}${template.name}${styles.reset}`,
|
|
3742
3711
|
`${styles.dim}Config:${styles.reset} ${truncatePath(configDir)}/config.json`,
|
|
3743
3712
|
`${styles.dim}CI Setup:${styles.reset} ${options.ci ? `Yes (${ciResult.provider || 'github'})` : 'No'}`,
|
|
@@ -3751,29 +3720,29 @@ async function initProject(projectPath, options) {
|
|
|
3751
3720
|
const recommendedCmds = frameworkResult.recommendedScans.map(scan => {
|
|
3752
3721
|
switch (scan) {
|
|
3753
3722
|
case 'secrets':
|
|
3754
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3723
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck scan:secrets${styles.reset} - Detect hardcoded credentials`;
|
|
3755
3724
|
case 'vuln':
|
|
3756
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3725
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck scan:vulnerabilities${styles.reset} - Check for CVEs`;
|
|
3757
3726
|
case 'ship':
|
|
3758
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3727
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck ship${styles.reset} - Pre-deployment readiness check`;
|
|
3759
3728
|
case 'reality':
|
|
3760
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3729
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck reality${styles.reset} - Browser testing for auth flows`;
|
|
3761
3730
|
case 'compliance':
|
|
3762
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3731
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck scan:compliance${styles.reset} - SOC2/GDPR compliance checks`;
|
|
3763
3732
|
default:
|
|
3764
|
-
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}
|
|
3733
|
+
return ` ${styles.cyan}${icons.bullet}${styles.reset} ${styles.bold}vibecheck ${scan}${styles.reset}`;
|
|
3765
3734
|
}
|
|
3766
3735
|
});
|
|
3767
3736
|
successLines.push(...recommendedCmds);
|
|
3768
3737
|
successLines.push('');
|
|
3769
|
-
successLines.push(`${styles.dim}Documentation:${styles.reset} ${styles.brightBlue}https://
|
|
3738
|
+
successLines.push(`${styles.dim}Documentation:${styles.reset} ${styles.brightBlue}https://vibecheckai.dev/docs${styles.reset}`);
|
|
3770
3739
|
const framedSuccess = frameLines(successLines, { padding: 2 });
|
|
3771
3740
|
console.log(framedSuccess.join('\n'));
|
|
3772
3741
|
console.log('');
|
|
3773
3742
|
// Show CI workflow path if created
|
|
3774
3743
|
if (options.ci && ciResult.workflowPath) {
|
|
3775
3744
|
console.log(` ${styles.dim}CI Workflow:${styles.reset} ${truncatePath(ciResult.workflowPath)}`);
|
|
3776
|
-
console.log(` ${styles.dim}Add${styles.reset} ${styles.brightCyan}
|
|
3745
|
+
console.log(` ${styles.dim}Add${styles.reset} ${styles.brightCyan}VIBECHECK_API_KEY${styles.reset} ${styles.dim}to your repository secrets${styles.reset}`);
|
|
3777
3746
|
console.log('');
|
|
3778
3747
|
}
|
|
3779
3748
|
// Show hooks info if installed
|
|
@@ -3957,7 +3926,7 @@ function outputComplianceResults(results, options) {
|
|
|
3957
3926
|
console.log('');
|
|
3958
3927
|
}
|
|
3959
3928
|
}
|
|
3960
|
-
console.log(` ${styles.dim}Run${styles.reset} ${styles.bold}
|
|
3929
|
+
console.log(` ${styles.dim}Run${styles.reset} ${styles.bold}vibecheck scan:compliance --framework gdpr${styles.reset} ${styles.dim}for other frameworks.${styles.reset}\n`);
|
|
3961
3930
|
}
|
|
3962
3931
|
/**
|
|
3963
3932
|
* Install Playwright dependencies automatically
|
|
@@ -4070,7 +4039,7 @@ async function runInteractiveMenu() {
|
|
|
4070
4039
|
continue;
|
|
4071
4040
|
}
|
|
4072
4041
|
// login
|
|
4073
|
-
const key = await promptPassword('Enter
|
|
4042
|
+
const key = await promptPassword('Enter vibecheck API key');
|
|
4074
4043
|
if (!key.startsWith('gr_') || key.length < 20) {
|
|
4075
4044
|
console.log(`\n${c.high('✗')} Invalid API key format`);
|
|
4076
4045
|
console.log(` ${c.dim('API keys should start with')} ${c.info('gr_')}\n`);
|
|
@@ -4097,7 +4066,7 @@ async function runInteractiveMenu() {
|
|
|
4097
4066
|
const projectPath = cfg.lastProjectPath || '.';
|
|
4098
4067
|
const { TruthPackGenerator } = await Promise.resolve().then(() => __importStar(require('./truth-pack')));
|
|
4099
4068
|
const generator = new TruthPackGenerator(projectPath);
|
|
4100
|
-
console.log(`\n${c.bold('🔧 INITIALIZING
|
|
4069
|
+
console.log(`\n${c.bold('🔧 INITIALIZING vibecheck')}\n`);
|
|
4101
4070
|
try {
|
|
4102
4071
|
const truthPack = await generator.generate();
|
|
4103
4072
|
console.log(` ${c.success('✓')} Truth Pack generated successfully!`);
|
|
@@ -4115,7 +4084,7 @@ async function runInteractiveMenu() {
|
|
|
4115
4084
|
const generator = new TruthPackGenerator(projectPath);
|
|
4116
4085
|
if (!generator.isFresh(168)) {
|
|
4117
4086
|
console.log(`\n${c.high('✗')} Truth Pack is stale or missing`);
|
|
4118
|
-
console.log(` ${c.dim('Run')} ${c.bold('
|
|
4087
|
+
console.log(` ${c.dim('Run')} ${c.bold('vibecheck init')} ${c.dim('first')}\n`);
|
|
4119
4088
|
continue;
|
|
4120
4089
|
}
|
|
4121
4090
|
console.log(`\n${c.bold('🚀 STARTING CONTEXT MODE')}\n`);
|
|
@@ -4127,7 +4096,7 @@ async function runInteractiveMenu() {
|
|
|
4127
4096
|
}
|
|
4128
4097
|
if (action === 'stats') {
|
|
4129
4098
|
const projectPath = cfg.lastProjectPath || '.';
|
|
4130
|
-
const statsFile = (0, path_2.join)(projectPath, '.
|
|
4099
|
+
const statsFile = (0, path_2.join)(projectPath, '.vibecheck', 'stats.json');
|
|
4131
4100
|
let stats;
|
|
4132
4101
|
if ((0, fs_1.existsSync)(statsFile)) {
|
|
4133
4102
|
try {
|
|
@@ -4140,12 +4109,12 @@ async function runInteractiveMenu() {
|
|
|
4140
4109
|
else {
|
|
4141
4110
|
stats = { hallucinationsBlocked: { last24h: 0, last7d: 0, total: 0 } };
|
|
4142
4111
|
}
|
|
4143
|
-
console.log(`\n${c.bold('📊
|
|
4112
|
+
console.log(`\n${c.bold('📊 vibecheck STATS')}\n`);
|
|
4144
4113
|
console.log(` ${c.bold('Hallucinations Blocked:')}`);
|
|
4145
4114
|
console.log(` Last 24h: ${c.bold(stats.hallucinationsBlocked?.last24h || 0)}`);
|
|
4146
4115
|
console.log(` Last 7d: ${c.bold(stats.hallucinationsBlocked?.last7d || 0)}`);
|
|
4147
4116
|
console.log(` Total: ${c.bold(stats.hallucinationsBlocked?.total || 0)}\n`);
|
|
4148
|
-
console.log(` ${c.bold('Next best action:')} ${c.info('
|
|
4117
|
+
console.log(` ${c.bold('Next best action:')} ${c.info('vibecheck ship')} to run ship check\n`);
|
|
4149
4118
|
continue;
|
|
4150
4119
|
}
|
|
4151
4120
|
if (action === 'checkpoint') {
|
|
@@ -4164,14 +4133,14 @@ async function runInteractiveMenu() {
|
|
|
4164
4133
|
console.log(` ${c.cyan('•')} Premium HTML reports`);
|
|
4165
4134
|
console.log(` ${c.cyan('•')} Proof artifacts\n`);
|
|
4166
4135
|
console.log(` ${c.bold('Price:')} $29/month\n`);
|
|
4167
|
-
console.log(` ${c.info('Upgrade now:')} ${c.bold('https://
|
|
4136
|
+
console.log(` ${c.info('Upgrade now:')} ${c.bold('https://vibecheckai.dev/upgrade')}\n`);
|
|
4168
4137
|
continue;
|
|
4169
4138
|
}
|
|
4170
4139
|
if (action === 'doctor') {
|
|
4171
4140
|
const projectPath = cfg.lastProjectPath || '.';
|
|
4172
4141
|
const { TruthPackGenerator } = await Promise.resolve().then(() => __importStar(require('./truth-pack')));
|
|
4173
4142
|
const generator = new TruthPackGenerator(projectPath);
|
|
4174
|
-
console.log(`\n${c.bold('🔧
|
|
4143
|
+
console.log(`\n${c.bold('🔧 vibecheck DOCTOR')}\n`);
|
|
4175
4144
|
const issues = [];
|
|
4176
4145
|
if (!generator.isFresh()) {
|
|
4177
4146
|
issues.push('Truth Pack is missing or stale');
|
|
@@ -4184,7 +4153,7 @@ async function runInteractiveMenu() {
|
|
|
4184
4153
|
issues.forEach(issue => {
|
|
4185
4154
|
console.log(` ${c.dim('•')} ${issue}`);
|
|
4186
4155
|
});
|
|
4187
|
-
console.log(`\n ${c.bold('Fix:')} Run ${c.info('
|
|
4156
|
+
console.log(`\n ${c.bold('Fix:')} Run ${c.info('vibecheck init')} to regenerate Truth Pack\n`);
|
|
4188
4157
|
}
|
|
4189
4158
|
continue;
|
|
4190
4159
|
}
|
|
@@ -4201,7 +4170,7 @@ async function runInteractiveMenu() {
|
|
|
4201
4170
|
]);
|
|
4202
4171
|
const writeOut = await promptConfirm('Write report file?', true);
|
|
4203
4172
|
const output = writeOut ? defaultReportPath(projectPath, 'secrets', 'json') : undefined;
|
|
4204
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4173
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck scan:secrets -p "${projectPath}" -f ${format}${output ? ` -o "${output}"` : ''}`)}\n`);
|
|
4205
4174
|
printLogo();
|
|
4206
4175
|
console.log(`\n${c.bold('🔐 SECRET DETECTION SCAN')}\n`);
|
|
4207
4176
|
const results = await scanSecrets(projectPath, { format, output });
|
|
@@ -4220,7 +4189,7 @@ async function runInteractiveMenu() {
|
|
|
4220
4189
|
]);
|
|
4221
4190
|
const writeOut = await promptConfirm('Write report file?', true);
|
|
4222
4191
|
const output = writeOut ? defaultReportPath(projectPath, 'vulns', 'json') : undefined;
|
|
4223
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4192
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck scan:vulnerabilities -p "${projectPath}" -f ${format}${output ? ` -o "${output}"` : ''}`)}\n`);
|
|
4224
4193
|
printLogo();
|
|
4225
4194
|
console.log(`\n${c.bold('🛡️ VULNERABILITY SCAN')}\n`);
|
|
4226
4195
|
const results = await scanVulnerabilities(projectPath, { format, output });
|
|
@@ -4246,7 +4215,7 @@ async function runInteractiveMenu() {
|
|
|
4246
4215
|
{ name: 'json', value: 'json' },
|
|
4247
4216
|
]);
|
|
4248
4217
|
saveConfig({ ...loadConfig(), lastFramework: framework, lastFormat: format });
|
|
4249
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4218
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck scan:compliance -p "${projectPath}" --framework ${framework} -f ${format}`)}\n`);
|
|
4250
4219
|
printLogo();
|
|
4251
4220
|
console.log(`\n${c.bold('📋 COMPLIANCE SCAN')}\n`);
|
|
4252
4221
|
const results = await scanCompliance(projectPath, { framework, format });
|
|
@@ -4262,7 +4231,7 @@ async function runInteractiveMenu() {
|
|
|
4262
4231
|
]);
|
|
4263
4232
|
const includeDev = await promptConfirm('Include dev dependencies?', false);
|
|
4264
4233
|
const output = defaultReportPath(projectPath, 'sbom', 'json');
|
|
4265
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4234
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck sbom:generate -p "${projectPath}" -f ${format} -o "${output}"${includeDev ? ' --include-dev' : ''}`)}\n`);
|
|
4266
4235
|
printLogo();
|
|
4267
4236
|
console.log(`\n${c.bold('📦 SBOM GENERATION')}\n`);
|
|
4268
4237
|
const sbom = await generateSBOM(projectPath, { format, includeDev, output });
|
|
@@ -4283,7 +4252,7 @@ async function runInteractiveMenu() {
|
|
|
4283
4252
|
{ name: 'Generate and run', value: 'run' },
|
|
4284
4253
|
{ name: 'Record user actions', value: 'record' },
|
|
4285
4254
|
]);
|
|
4286
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4255
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck reality --url "${url}" --flow ${flow}${mode === 'run' ? ' --run' : mode === 'record' ? ' --record' : ''}`)}\n`);
|
|
4287
4256
|
printLogo();
|
|
4288
4257
|
console.log(`\n${c.bold('🌐 REALITY MODE')}\n`);
|
|
4289
4258
|
// Check dependencies and install if needed
|
|
@@ -4319,7 +4288,7 @@ async function runInteractiveMenu() {
|
|
|
4319
4288
|
args.push('--run');
|
|
4320
4289
|
if (mode === 'record')
|
|
4321
4290
|
args.push('--record');
|
|
4322
|
-
const realityProc = spawn('
|
|
4291
|
+
const realityProc = spawn('vibecheck', args, {
|
|
4323
4292
|
stdio: 'inherit',
|
|
4324
4293
|
shell: process.platform === 'win32',
|
|
4325
4294
|
cwd: projectPath
|
|
@@ -4339,14 +4308,14 @@ async function runInteractiveMenu() {
|
|
|
4339
4308
|
const baseline = await promptConfirm('Use baseline file?', false);
|
|
4340
4309
|
const output = await promptConfirm('Generate ship report?', true);
|
|
4341
4310
|
const outputPath = output ? defaultReportPath(projectPath, 'ship', 'json') : undefined;
|
|
4342
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4311
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck ship -p "${projectPath}"${baseline ? ' --baseline .vibecheck/baseline.json' : ''}${outputPath ? ` --output "${outputPath}"` : ''}`)}\n`);
|
|
4343
4312
|
printLogo();
|
|
4344
4313
|
console.log(`\n${c.bold('🚀 SHIP CHECK')}\n`);
|
|
4345
4314
|
// Import ship functionality
|
|
4346
|
-
const { runShipCheck } = require('./bundles/
|
|
4315
|
+
const { runShipCheck } = require('./bundles/vibecheck-ship');
|
|
4347
4316
|
try {
|
|
4348
4317
|
const shipResult = await runShipCheck(projectPath, {
|
|
4349
|
-
baseline: baseline ? '.
|
|
4318
|
+
baseline: baseline ? '.vibecheck/baseline.json' : undefined,
|
|
4350
4319
|
output: outputPath
|
|
4351
4320
|
});
|
|
4352
4321
|
if (shipResult.verdict === 'ship') {
|
|
@@ -4373,7 +4342,7 @@ async function runInteractiveMenu() {
|
|
|
4373
4342
|
]);
|
|
4374
4343
|
const setupCI = await promptConfirm('Setup CI/CD integration?', false);
|
|
4375
4344
|
const setupHooks = await promptConfirm('Install git hooks?', false);
|
|
4376
|
-
console.log(`\n${c.dim('Command:')} ${c.bold(`
|
|
4345
|
+
console.log(`\n${c.dim('Command:')} ${c.bold(`vibecheck init -p "${projectPath}" --template ${template}${setupCI ? ' --ci' : ''}${setupHooks ? ' --hooks' : ''}`)}\n`);
|
|
4377
4346
|
printLogo();
|
|
4378
4347
|
console.log(`\n${c.bold('🔧 INITIALIZING PROJECT')}\n`);
|
|
4379
4348
|
try {
|
|
@@ -4395,26 +4364,9 @@ async function runInteractiveMenu() {
|
|
|
4395
4364
|
}
|
|
4396
4365
|
// Register cache management commands
|
|
4397
4366
|
(0, cache_1.registerCacheCommands)(program, printLogo);
|
|
4398
|
-
//
|
|
4399
|
-
|
|
4400
|
-
|
|
4401
|
-
(0, stats_1.registerStatsCommand)(program);
|
|
4402
|
-
(0, checkpoint_1.registerCheckpointCommand)(program);
|
|
4403
|
-
(0, upgrade_1.registerUpgradeCommand)(program);
|
|
4404
|
-
// Register consolidated scan/ship/fix commands
|
|
4405
|
-
const scan_consolidated_1 = require("./commands/scan-consolidated");
|
|
4406
|
-
const ship_consolidated_1 = require("./commands/ship-consolidated");
|
|
4407
|
-
const fix_consolidated_1 = require("./commands/fix-consolidated");
|
|
4408
|
-
const explain_1 = require("./commands/explain");
|
|
4409
|
-
const replay_1 = require("./commands/replay");
|
|
4410
|
-
(0, scan_consolidated_1.registerScanCommand)(program);
|
|
4411
|
-
(0, ship_consolidated_1.registerShipCommand)(program);
|
|
4412
|
-
(0, fix_consolidated_1.registerFixCommand)(program);
|
|
4413
|
-
(0, explain_1.registerExplainCommand)(program);
|
|
4414
|
-
(0, replay_1.registerReplayCommand)(program);
|
|
4415
|
-
// Register doctor command
|
|
4416
|
-
const doctor_1 = require("./commands/doctor");
|
|
4417
|
-
(0, doctor_1.registerDoctorCommand)(program);
|
|
4367
|
+
// NOTE: Core commands (init, scan, ship, fix, etc.) are defined inline above
|
|
4368
|
+
// The registerXCommand functions are NOT called here to avoid duplicates
|
|
4369
|
+
// If you need to use modular command files, remove the inline definitions first
|
|
4418
4370
|
// Menu command
|
|
4419
4371
|
program
|
|
4420
4372
|
.command('menu')
|