@vibecheckai/cli 3.5.0 → 3.5.2
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/bin/registry.js +214 -237
- package/bin/runners/cli-utils.js +33 -2
- package/bin/runners/context/analyzer.js +52 -1
- package/bin/runners/context/generators/cursor.js +2 -49
- package/bin/runners/context/git-context.js +3 -1
- package/bin/runners/context/team-conventions.js +33 -7
- package/bin/runners/lib/analysis-core.js +25 -5
- package/bin/runners/lib/analyzers.js +431 -481
- package/bin/runners/lib/default-config.js +127 -0
- package/bin/runners/lib/doctor/modules/security.js +3 -1
- package/bin/runners/lib/engine/ast-cache.js +210 -0
- package/bin/runners/lib/engine/auth-extractor.js +211 -0
- package/bin/runners/lib/engine/billing-extractor.js +112 -0
- package/bin/runners/lib/engine/enforcement-extractor.js +100 -0
- package/bin/runners/lib/engine/env-extractor.js +207 -0
- package/bin/runners/lib/engine/express-extractor.js +208 -0
- package/bin/runners/lib/engine/extractors.js +849 -0
- package/bin/runners/lib/engine/index.js +207 -0
- package/bin/runners/lib/engine/repo-index.js +514 -0
- package/bin/runners/lib/engine/types.js +124 -0
- package/bin/runners/lib/engines/accessibility-engine.js +18 -218
- package/bin/runners/lib/engines/api-consistency-engine.js +30 -335
- package/bin/runners/lib/engines/cross-file-analysis-engine.js +27 -292
- package/bin/runners/lib/engines/empty-catch-engine.js +17 -127
- package/bin/runners/lib/engines/mock-data-engine.js +10 -53
- package/bin/runners/lib/engines/performance-issues-engine.js +36 -176
- package/bin/runners/lib/engines/security-vulnerabilities-engine.js +54 -382
- package/bin/runners/lib/engines/type-aware-engine.js +39 -263
- package/bin/runners/lib/engines/vibecheck-engines/index.js +13 -122
- package/bin/runners/lib/engines/vibecheck-engines/lib/ast-cache.js +164 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/code-quality-engine.js +291 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/console-logs-engine.js +83 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/dead-code-engine.js +198 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/deprecated-api-engine.js +275 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/empty-catch-engine.js +167 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/file-filter.js +217 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/hardcoded-secrets-engine.js +73 -373
- package/bin/runners/lib/engines/vibecheck-engines/lib/mock-data-engine.js +140 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/parallel-processor.js +164 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/performance-issues-engine.js +234 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/type-aware-engine.js +217 -0
- package/bin/runners/lib/engines/vibecheck-engines/lib/unsafe-regex-engine.js +78 -0
- package/bin/runners/lib/entitlements-v2.js +73 -97
- package/bin/runners/lib/error-handler.js +44 -3
- package/bin/runners/lib/error-messages.js +289 -0
- package/bin/runners/lib/evidence-pack.js +7 -1
- package/bin/runners/lib/finding-id.js +69 -0
- package/bin/runners/lib/finding-sorter.js +89 -0
- package/bin/runners/lib/html-proof-report.js +700 -350
- package/bin/runners/lib/missions/plan.js +6 -46
- package/bin/runners/lib/missions/templates.js +0 -232
- package/bin/runners/lib/next-action.js +560 -0
- package/bin/runners/lib/prerequisites.js +149 -0
- package/bin/runners/lib/route-detection.js +137 -68
- package/bin/runners/lib/scan-output.js +91 -76
- package/bin/runners/lib/scan-runner.js +135 -0
- package/bin/runners/lib/schemas/ajv-validator.js +464 -0
- package/bin/runners/lib/schemas/error-envelope.schema.json +105 -0
- package/bin/runners/lib/schemas/finding-v3.schema.json +151 -0
- package/bin/runners/lib/schemas/report-artifact.schema.json +120 -0
- package/bin/runners/lib/schemas/run-request.schema.json +108 -0
- package/bin/runners/lib/schemas/validator.js +27 -0
- package/bin/runners/lib/schemas/verdict.schema.json +140 -0
- package/bin/runners/lib/ship-output-enterprise.js +23 -23
- package/bin/runners/lib/ship-output.js +75 -31
- package/bin/runners/lib/terminal-ui.js +6 -113
- package/bin/runners/lib/truth.js +351 -10
- package/bin/runners/lib/unified-cli-output.js +430 -603
- package/bin/runners/lib/unified-output.js +13 -9
- package/bin/runners/runAIAgent.js +10 -5
- package/bin/runners/runAgent.js +0 -3
- package/bin/runners/runAllowlist.js +389 -0
- package/bin/runners/runApprove.js +0 -33
- package/bin/runners/runAuth.js +73 -45
- package/bin/runners/runCheckpoint.js +51 -11
- package/bin/runners/runClassify.js +85 -21
- package/bin/runners/runContext.js +0 -3
- package/bin/runners/runDoctor.js +41 -28
- package/bin/runners/runEvidencePack.js +362 -0
- package/bin/runners/runFirewall.js +0 -3
- package/bin/runners/runFirewallHook.js +0 -3
- package/bin/runners/runFix.js +66 -76
- package/bin/runners/runGuard.js +18 -411
- package/bin/runners/runInit.js +113 -30
- package/bin/runners/runLabs.js +424 -0
- package/bin/runners/runMcp.js +19 -25
- package/bin/runners/runPolish.js +64 -240
- package/bin/runners/runPromptFirewall.js +12 -5
- package/bin/runners/runProve.js +57 -22
- package/bin/runners/runQuickstart.js +531 -0
- package/bin/runners/runReality.js +59 -68
- package/bin/runners/runReport.js +38 -33
- package/bin/runners/runRuntime.js +8 -5
- package/bin/runners/runScan.js +1413 -190
- package/bin/runners/runShip.js +113 -719
- package/bin/runners/runTruth.js +0 -3
- package/bin/runners/runValidate.js +13 -9
- package/bin/runners/runWatch.js +23 -14
- package/bin/scan.js +6 -1
- package/bin/vibecheck.js +204 -185
- package/mcp-server/deprecation-middleware.js +282 -0
- package/mcp-server/handlers/index.ts +15 -0
- package/mcp-server/handlers/tool-handler.ts +554 -0
- package/mcp-server/index-v1.js +698 -0
- package/mcp-server/index.js +210 -238
- package/mcp-server/lib/cache-wrapper.cjs +383 -0
- package/mcp-server/lib/error-envelope.js +138 -0
- package/mcp-server/lib/executor.ts +499 -0
- package/mcp-server/lib/index.ts +19 -0
- package/mcp-server/lib/rate-limiter.js +166 -0
- package/mcp-server/lib/sandbox.test.ts +519 -0
- package/mcp-server/lib/sandbox.ts +395 -0
- package/mcp-server/lib/types.ts +267 -0
- package/mcp-server/package.json +12 -3
- package/mcp-server/registry/tool-registry.js +794 -0
- package/mcp-server/registry/tools.json +605 -0
- package/mcp-server/registry.test.ts +334 -0
- package/mcp-server/tests/tier-gating.test.js +297 -0
- package/mcp-server/tier-auth.js +378 -45
- package/mcp-server/tools-v3.js +353 -442
- package/mcp-server/tsconfig.json +37 -0
- package/mcp-server/vibecheck-2.0-tools.js +14 -1
- package/package.json +1 -1
- package/bin/runners/lib/agent-firewall/learning/learning-engine.js +0 -849
- package/bin/runners/lib/audit-logger.js +0 -532
- package/bin/runners/lib/authority/authorities/architecture.js +0 -364
- package/bin/runners/lib/authority/authorities/compliance.js +0 -341
- package/bin/runners/lib/authority/authorities/human.js +0 -343
- package/bin/runners/lib/authority/authorities/quality.js +0 -420
- package/bin/runners/lib/authority/authorities/security.js +0 -228
- package/bin/runners/lib/authority/index.js +0 -293
- package/bin/runners/lib/bundle/bundle-intelligence.js +0 -846
- package/bin/runners/lib/cli-charts.js +0 -368
- package/bin/runners/lib/cli-config-display.js +0 -405
- package/bin/runners/lib/cli-demo.js +0 -275
- package/bin/runners/lib/cli-errors.js +0 -438
- package/bin/runners/lib/cli-help-formatter.js +0 -439
- package/bin/runners/lib/cli-interactive-menu.js +0 -509
- package/bin/runners/lib/cli-prompts.js +0 -441
- package/bin/runners/lib/cli-scan-cards.js +0 -362
- package/bin/runners/lib/compliance-reporter.js +0 -710
- package/bin/runners/lib/conductor/index.js +0 -671
- package/bin/runners/lib/easy/README.md +0 -123
- package/bin/runners/lib/easy/index.js +0 -140
- package/bin/runners/lib/easy/interactive-wizard.js +0 -788
- package/bin/runners/lib/easy/one-click-firewall.js +0 -564
- package/bin/runners/lib/easy/zero-config-reality.js +0 -714
- package/bin/runners/lib/engines/async-patterns-engine.js +0 -444
- package/bin/runners/lib/engines/bundle-size-engine.js +0 -433
- package/bin/runners/lib/engines/confidence-scoring.js +0 -276
- package/bin/runners/lib/engines/context-detection.js +0 -264
- package/bin/runners/lib/engines/database-patterns-engine.js +0 -429
- package/bin/runners/lib/engines/duplicate-code-engine.js +0 -354
- package/bin/runners/lib/engines/env-variables-engine.js +0 -458
- package/bin/runners/lib/engines/error-handling-engine.js +0 -437
- package/bin/runners/lib/engines/false-positive-prevention.js +0 -630
- package/bin/runners/lib/engines/framework-adapters/index.js +0 -607
- package/bin/runners/lib/engines/framework-detection.js +0 -508
- package/bin/runners/lib/engines/import-order-engine.js +0 -429
- package/bin/runners/lib/engines/naming-conventions-engine.js +0 -544
- package/bin/runners/lib/engines/noise-reduction-engine.js +0 -452
- package/bin/runners/lib/engines/orchestrator.js +0 -334
- package/bin/runners/lib/engines/react-patterns-engine.js +0 -457
- package/bin/runners/lib/engines/vibecheck-engines/lib/ai-hallucination-engine.js +0 -806
- package/bin/runners/lib/engines/vibecheck-engines/lib/smart-fix-engine.js +0 -577
- package/bin/runners/lib/engines/vibecheck-engines/lib/vibe-score-engine.js +0 -543
- package/bin/runners/lib/engines/vibecheck-engines.js +0 -514
- package/bin/runners/lib/enhanced-features/index.js +0 -305
- package/bin/runners/lib/enhanced-output.js +0 -631
- package/bin/runners/lib/enterprise.js +0 -300
- package/bin/runners/lib/firewall/command-validator.js +0 -351
- package/bin/runners/lib/firewall/config.js +0 -341
- package/bin/runners/lib/firewall/content-validator.js +0 -519
- package/bin/runners/lib/firewall/index.js +0 -101
- package/bin/runners/lib/firewall/path-validator.js +0 -256
- package/bin/runners/lib/intelligence/cross-repo-intelligence.js +0 -817
- package/bin/runners/lib/mcp-utils.js +0 -425
- package/bin/runners/lib/output/index.js +0 -1022
- package/bin/runners/lib/policy-engine.js +0 -652
- package/bin/runners/lib/polish/autofix/accessibility-fixes.js +0 -333
- package/bin/runners/lib/polish/autofix/async-handlers.js +0 -273
- package/bin/runners/lib/polish/autofix/dead-code.js +0 -280
- package/bin/runners/lib/polish/autofix/imports-optimizer.js +0 -344
- package/bin/runners/lib/polish/autofix/index.js +0 -200
- package/bin/runners/lib/polish/autofix/remove-consoles.js +0 -209
- package/bin/runners/lib/polish/autofix/strengthen-types.js +0 -245
- package/bin/runners/lib/polish/backend-checks.js +0 -148
- package/bin/runners/lib/polish/documentation-checks.js +0 -111
- package/bin/runners/lib/polish/frontend-checks.js +0 -168
- package/bin/runners/lib/polish/index.js +0 -71
- package/bin/runners/lib/polish/infrastructure-checks.js +0 -131
- package/bin/runners/lib/polish/library-detection.js +0 -175
- package/bin/runners/lib/polish/performance-checks.js +0 -100
- package/bin/runners/lib/polish/security-checks.js +0 -148
- package/bin/runners/lib/polish/utils.js +0 -203
- package/bin/runners/lib/prompt-builder.js +0 -540
- package/bin/runners/lib/proof-certificate.js +0 -634
- package/bin/runners/lib/reality/accessibility-audit.js +0 -946
- package/bin/runners/lib/reality/api-contract-validator.js +0 -1012
- package/bin/runners/lib/reality/chaos-engineering.js +0 -1084
- package/bin/runners/lib/reality/performance-tracker.js +0 -1077
- package/bin/runners/lib/reality/scenario-generator.js +0 -1404
- package/bin/runners/lib/reality/visual-regression.js +0 -852
- package/bin/runners/lib/reality-profiler.js +0 -717
- package/bin/runners/lib/replay/flight-recorder-viewer.js +0 -1160
- package/bin/runners/lib/review/ai-code-review.js +0 -832
- package/bin/runners/lib/rules/custom-rule-engine.js +0 -985
- package/bin/runners/lib/sbom-generator.js +0 -641
- package/bin/runners/lib/scan-output-enhanced.js +0 -512
- package/bin/runners/lib/security/owasp-scanner.js +0 -939
- package/bin/runners/lib/validators/contract-validator.js +0 -283
- package/bin/runners/lib/validators/dead-export-detector.js +0 -279
- package/bin/runners/lib/validators/dep-audit.js +0 -245
- package/bin/runners/lib/validators/env-validator.js +0 -319
- package/bin/runners/lib/validators/index.js +0 -120
- package/bin/runners/lib/validators/license-checker.js +0 -252
- package/bin/runners/lib/validators/route-validator.js +0 -290
- package/bin/runners/runAuthority.js +0 -528
- package/bin/runners/runConductor.js +0 -772
- package/bin/runners/runContainer.js +0 -366
- package/bin/runners/runEasy.js +0 -410
- package/bin/runners/runIaC.js +0 -372
- package/bin/runners/runVibe.js +0 -791
- package/mcp-server/tools.js +0 -495
|
@@ -1,528 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* vibecheck authority - Authority System CLI
|
|
3
|
-
*
|
|
4
|
-
* List authorities and request approvals from human or automated reviewers.
|
|
5
|
-
*
|
|
6
|
-
* Usage:
|
|
7
|
-
* vibecheck authority list - List available authorities
|
|
8
|
-
* vibecheck authority approve --authority security - Request security approval
|
|
9
|
-
* vibecheck authority approve --authority quality - Request quality approval
|
|
10
|
-
*
|
|
11
|
-
* Part of the Authority System - "The AI That Says No"
|
|
12
|
-
*/
|
|
13
|
-
|
|
14
|
-
"use strict";
|
|
15
|
-
|
|
16
|
-
const path = require("path");
|
|
17
|
-
const fs = require("fs");
|
|
18
|
-
const { withErrorHandling, createUserError } = require("./lib/error-handler");
|
|
19
|
-
const { parseGlobalFlags, shouldShowBanner } = require("./lib/global-flags");
|
|
20
|
-
const { EXIT } = require("./lib/exit-codes");
|
|
21
|
-
|
|
22
|
-
// Authority module
|
|
23
|
-
const {
|
|
24
|
-
listAuthorities,
|
|
25
|
-
requestApproval,
|
|
26
|
-
requestMultipleApprovals,
|
|
27
|
-
getAggregatedVerdict,
|
|
28
|
-
hasAuthority,
|
|
29
|
-
} = require("./lib/authority");
|
|
30
|
-
|
|
31
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
32
|
-
// TERMINAL UI
|
|
33
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
34
|
-
|
|
35
|
-
const {
|
|
36
|
-
ansi,
|
|
37
|
-
colors,
|
|
38
|
-
Spinner,
|
|
39
|
-
} = require("./lib/terminal-ui");
|
|
40
|
-
|
|
41
|
-
// Unified Output System
|
|
42
|
-
const { output } = require("./lib/output/index.js");
|
|
43
|
-
|
|
44
|
-
const BANNER = `
|
|
45
|
-
${ansi.rgb(0, 200, 255)} ██╗ ██╗██╗██████╗ ███████╗ ██████╗██╗ ██╗███████╗ ██████╗██╗ ██╗${ansi.reset}
|
|
46
|
-
${ansi.rgb(30, 180, 255)} ██║ ██║██║██╔══██╗██╔════╝██╔════╝██║ ██║██╔════╝██╔════╝██║ ██╔╝${ansi.reset}
|
|
47
|
-
${ansi.rgb(60, 160, 255)} ██║ ██║██║██████╔╝█████╗ ██║ ███████║█████╗ ██║ █████╔╝ ${ansi.reset}
|
|
48
|
-
${ansi.rgb(90, 140, 255)} ╚██╗ ██╔╝██║██╔══██╗██╔══╝ ██║ ██╔══██║██╔══╝ ██║ ██╔═██╗ ${ansi.reset}
|
|
49
|
-
${ansi.rgb(120, 120, 255)} ╚████╔╝ ██║██████╔╝███████╗╚██████╗██║ ██║███████╗╚██████╗██║ ██╗${ansi.reset}
|
|
50
|
-
${ansi.rgb(150, 100, 255)} ╚═══╝ ╚═╝╚═════╝ ╚══════╝ ╚═════╝╚═╝ ╚═╝╚══════╝ ╚═════╝╚═╝ ╚═╝${ansi.reset}
|
|
51
|
-
|
|
52
|
-
${ansi.dim} ┌─────────────────────────────────────────────────────────────────────┐${ansi.reset}
|
|
53
|
-
${ansi.dim} │${ansi.reset} ${ansi.rgb(255, 255, 255)}${ansi.bold}Authority System${ansi.reset} ${ansi.dim}•${ansi.reset} ${ansi.rgb(200, 200, 200)}The AI That Says No${ansi.reset} ${ansi.dim}│${ansi.reset}
|
|
54
|
-
${ansi.dim} └─────────────────────────────────────────────────────────────────────┘${ansi.reset}
|
|
55
|
-
`;
|
|
56
|
-
|
|
57
|
-
function printBanner() {
|
|
58
|
-
console.log(BANNER);
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
62
|
-
// ARGS PARSER
|
|
63
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
64
|
-
|
|
65
|
-
function parseArgs(args) {
|
|
66
|
-
const { flags: globalFlags, cleanArgs } = parseGlobalFlags(args);
|
|
67
|
-
|
|
68
|
-
const opts = {
|
|
69
|
-
path: globalFlags.path || process.cwd(),
|
|
70
|
-
json: globalFlags.json || false,
|
|
71
|
-
verbose: globalFlags.verbose || false,
|
|
72
|
-
help: globalFlags.help || false,
|
|
73
|
-
noBanner: globalFlags.noBanner || false,
|
|
74
|
-
ci: globalFlags.ci || false,
|
|
75
|
-
quiet: globalFlags.quiet || false,
|
|
76
|
-
// Subcommand
|
|
77
|
-
subcommand: null, // 'list' or 'approve'
|
|
78
|
-
// Authority options
|
|
79
|
-
authority: null,
|
|
80
|
-
authorities: [], // For multi-authority approval
|
|
81
|
-
// File input
|
|
82
|
-
files: [],
|
|
83
|
-
diff: null,
|
|
84
|
-
diffFile: null,
|
|
85
|
-
// Output
|
|
86
|
-
output: null,
|
|
87
|
-
};
|
|
88
|
-
|
|
89
|
-
for (let i = 0; i < cleanArgs.length; i++) {
|
|
90
|
-
const arg = cleanArgs[i];
|
|
91
|
-
|
|
92
|
-
// Subcommands
|
|
93
|
-
if (arg === 'list' && !opts.subcommand) {
|
|
94
|
-
opts.subcommand = 'list';
|
|
95
|
-
} else if (arg === 'approve' && !opts.subcommand) {
|
|
96
|
-
opts.subcommand = 'approve';
|
|
97
|
-
}
|
|
98
|
-
// Options
|
|
99
|
-
else if (arg === '--authority' || arg === '-a') {
|
|
100
|
-
const value = cleanArgs[++i];
|
|
101
|
-
if (value) {
|
|
102
|
-
opts.authority = value;
|
|
103
|
-
if (!opts.authorities.includes(value)) {
|
|
104
|
-
opts.authorities.push(value);
|
|
105
|
-
}
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
else if (arg.startsWith('--authority=')) {
|
|
109
|
-
const value = arg.split('=')[1];
|
|
110
|
-
opts.authority = value;
|
|
111
|
-
if (!opts.authorities.includes(value)) {
|
|
112
|
-
opts.authorities.push(value);
|
|
113
|
-
}
|
|
114
|
-
}
|
|
115
|
-
else if (arg === '--file' || arg === '-f') {
|
|
116
|
-
const value = cleanArgs[++i];
|
|
117
|
-
if (value) opts.files.push(value);
|
|
118
|
-
}
|
|
119
|
-
else if (arg === '--diff') {
|
|
120
|
-
opts.diff = cleanArgs[++i];
|
|
121
|
-
}
|
|
122
|
-
else if (arg === '--diff-file') {
|
|
123
|
-
opts.diffFile = cleanArgs[++i];
|
|
124
|
-
}
|
|
125
|
-
else if (arg === '--output' || arg === '-o') {
|
|
126
|
-
opts.output = cleanArgs[++i];
|
|
127
|
-
}
|
|
128
|
-
else if (arg === '--path' || arg === '-p') {
|
|
129
|
-
opts.path = cleanArgs[++i] || process.cwd();
|
|
130
|
-
}
|
|
131
|
-
else if (arg.startsWith('--path=')) {
|
|
132
|
-
opts.path = arg.split('=')[1];
|
|
133
|
-
}
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
// Default subcommand
|
|
137
|
-
if (!opts.subcommand) {
|
|
138
|
-
opts.subcommand = 'list';
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
return opts;
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
function printHelp(showBanner = true) {
|
|
145
|
-
if (showBanner && shouldShowBanner({})) {
|
|
146
|
-
printBanner();
|
|
147
|
-
}
|
|
148
|
-
console.log(`
|
|
149
|
-
${ansi.bold}USAGE${ansi.reset}
|
|
150
|
-
${colors.accent}vibecheck authority${ansi.reset} <subcommand> [options]
|
|
151
|
-
|
|
152
|
-
${ansi.bold}SUBCOMMANDS${ansi.reset}
|
|
153
|
-
${colors.accent}list${ansi.reset} List all available authorities
|
|
154
|
-
${colors.accent}approve${ansi.reset} Request approval from an authority
|
|
155
|
-
|
|
156
|
-
${ansi.bold}AUTHORITY OPTIONS${ansi.reset}
|
|
157
|
-
${colors.accent}--authority, -a${ansi.reset} Authority to request approval from
|
|
158
|
-
Can be specified multiple times for multi-approval
|
|
159
|
-
|
|
160
|
-
${ansi.bold}INPUT OPTIONS${ansi.reset}
|
|
161
|
-
${colors.accent}--file, -f${ansi.reset} File to include in review (can be repeated)
|
|
162
|
-
${colors.accent}--diff${ansi.reset} Git diff string to review
|
|
163
|
-
${colors.accent}--diff-file${ansi.reset} Read diff from file
|
|
164
|
-
|
|
165
|
-
${ansi.bold}OUTPUT OPTIONS${ansi.reset}
|
|
166
|
-
${colors.accent}--json${ansi.reset} Output as JSON
|
|
167
|
-
${colors.accent}--output, -o${ansi.reset} Save result to file
|
|
168
|
-
|
|
169
|
-
${ansi.bold}GLOBAL OPTIONS${ansi.reset}
|
|
170
|
-
${colors.accent}--path, -p <dir>${ansi.reset} Run in specified directory
|
|
171
|
-
${colors.accent}--verbose, -v${ansi.reset} Show detailed output
|
|
172
|
-
${colors.accent}--quiet, -q${ansi.reset} Suppress non-essential output
|
|
173
|
-
${colors.accent}--ci${ansi.reset} CI mode (quiet + exit codes)
|
|
174
|
-
${colors.accent}--help, -h${ansi.reset} Show this help
|
|
175
|
-
|
|
176
|
-
${ansi.bold}💡 EXAMPLES${ansi.reset}
|
|
177
|
-
|
|
178
|
-
${ansi.dim}# List available authorities${ansi.reset}
|
|
179
|
-
vibecheck authority list
|
|
180
|
-
|
|
181
|
-
${ansi.dim}# Request security review${ansi.reset}
|
|
182
|
-
vibecheck authority approve --authority security
|
|
183
|
-
|
|
184
|
-
${ansi.dim}# Review specific files${ansi.reset}
|
|
185
|
-
vibecheck authority approve -a security -f src/auth.ts -f src/login.ts
|
|
186
|
-
|
|
187
|
-
${ansi.dim}# Review a diff${ansi.reset}
|
|
188
|
-
git diff HEAD~1 | vibecheck authority approve -a security --diff-file -
|
|
189
|
-
|
|
190
|
-
${ansi.dim}# Multi-authority approval${ansi.reset}
|
|
191
|
-
vibecheck authority approve -a security -a quality -a architecture
|
|
192
|
-
|
|
193
|
-
${ansi.dim}# JSON output for CI${ansi.reset}
|
|
194
|
-
vibecheck authority approve -a security --json --ci
|
|
195
|
-
|
|
196
|
-
${ansi.bold}📊 VERDICTS${ansi.reset}
|
|
197
|
-
${colors.success}APPROVED${ansi.reset} Review passed (exit 0)
|
|
198
|
-
${colors.error}REJECTED${ansi.reset} Issues found (exit 1)
|
|
199
|
-
${colors.warning}PENDING${ansi.reset} Awaiting human approval (exit 2)
|
|
200
|
-
|
|
201
|
-
${ansi.bold}🔗 RELATED COMMANDS${ansi.reset}
|
|
202
|
-
${colors.accent}vibecheck approve${ansi.reset} Authority verdicts ${ansi.dim}(alias)${ansi.reset}
|
|
203
|
-
${colors.accent}vibecheck scan${ansi.reset} Full code analysis
|
|
204
|
-
${colors.accent}vibecheck ship${ansi.reset} SHIP/WARN/BLOCK verdict
|
|
205
|
-
|
|
206
|
-
${ansi.dim}─────────────────────────────────────────────────────────────${ansi.reset}
|
|
207
|
-
${ansi.dim}Documentation: https://docs.vibecheckai.dev/cli/authority${ansi.reset}
|
|
208
|
-
`);
|
|
209
|
-
}
|
|
210
|
-
|
|
211
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
212
|
-
// LIST COMMAND
|
|
213
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
214
|
-
|
|
215
|
-
async function runAuthorityList(opts) {
|
|
216
|
-
const authorities = await listAuthorities();
|
|
217
|
-
|
|
218
|
-
if (opts.json) {
|
|
219
|
-
console.log(JSON.stringify(authorities, null, 2));
|
|
220
|
-
return 0;
|
|
221
|
-
}
|
|
222
|
-
|
|
223
|
-
console.log(`\n ${ansi.bold}Available Authorities${ansi.reset}\n`);
|
|
224
|
-
console.log(` ┌${"─".repeat(66)}┐`);
|
|
225
|
-
console.log(` │ ${"Authority".padEnd(14)} │ ${"Description".padEnd(35)} │ ${"Type".padEnd(6)} │ ${"Tier".padEnd(4)} │`);
|
|
226
|
-
console.log(` ├${"─".repeat(66)}┤`);
|
|
227
|
-
|
|
228
|
-
for (const auth of authorities) {
|
|
229
|
-
const typeLabel = auth.automated ? "Auto" : "Human";
|
|
230
|
-
const typeColor = auth.automated ? colors.success : colors.warning;
|
|
231
|
-
const tierColor = auth.tier === "free" ? colors.success : colors.accent;
|
|
232
|
-
|
|
233
|
-
console.log(
|
|
234
|
-
` │ ${colors.accent}${auth.name.padEnd(14)}${ansi.reset} │ ${auth.description.slice(0, 35).padEnd(35)} │ ${typeColor}${typeLabel.padEnd(6)}${ansi.reset} │ ${tierColor}${auth.tier.padEnd(4)}${ansi.reset} │`
|
|
235
|
-
);
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
console.log(` └${"─".repeat(66)}┘`);
|
|
239
|
-
console.log();
|
|
240
|
-
console.log(` ${ansi.dim}Usage: vibecheck authority approve --authority <name>${ansi.reset}`);
|
|
241
|
-
console.log();
|
|
242
|
-
|
|
243
|
-
return 0;
|
|
244
|
-
}
|
|
245
|
-
|
|
246
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
247
|
-
// APPROVE COMMAND
|
|
248
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
249
|
-
|
|
250
|
-
async function runAuthorityApprove(opts) {
|
|
251
|
-
const projectPath = path.resolve(opts.path);
|
|
252
|
-
|
|
253
|
-
// Validate authority
|
|
254
|
-
if (opts.authorities.length === 0) {
|
|
255
|
-
if (!opts.authority) {
|
|
256
|
-
console.error(`\n ${colors.error}✗${ansi.reset} Authority required\n`);
|
|
257
|
-
console.log(` ${ansi.dim}Usage: vibecheck authority approve --authority <name>${ansi.reset}`);
|
|
258
|
-
console.log(` ${ansi.dim}List: vibecheck authority list${ansi.reset}\n`);
|
|
259
|
-
return EXIT.USER_ERROR;
|
|
260
|
-
}
|
|
261
|
-
opts.authorities = [opts.authority];
|
|
262
|
-
}
|
|
263
|
-
|
|
264
|
-
// Validate all authorities exist
|
|
265
|
-
for (const auth of opts.authorities) {
|
|
266
|
-
if (!hasAuthority(auth)) {
|
|
267
|
-
const authorities = await listAuthorities();
|
|
268
|
-
console.error(`\n ${colors.error}✗${ansi.reset} Unknown authority: ${auth}\n`);
|
|
269
|
-
console.log(` ${ansi.dim}Available: ${authorities.map(a => a.name).join(", ")}${ansi.reset}\n`);
|
|
270
|
-
return EXIT.USER_ERROR;
|
|
271
|
-
}
|
|
272
|
-
}
|
|
273
|
-
|
|
274
|
-
// Build payload
|
|
275
|
-
const payload = {
|
|
276
|
-
files: [],
|
|
277
|
-
diff: opts.diff || "",
|
|
278
|
-
context: {
|
|
279
|
-
projectPath,
|
|
280
|
-
branch: process.env.GITHUB_HEAD_REF || process.env.BRANCH_NAME,
|
|
281
|
-
commit: process.env.GITHUB_SHA || process.env.COMMIT_SHA,
|
|
282
|
-
},
|
|
283
|
-
};
|
|
284
|
-
|
|
285
|
-
// Load files
|
|
286
|
-
for (const filePath of opts.files) {
|
|
287
|
-
const fullPath = path.resolve(projectPath, filePath);
|
|
288
|
-
try {
|
|
289
|
-
const content = fs.readFileSync(fullPath, "utf-8");
|
|
290
|
-
payload.files.push({
|
|
291
|
-
path: filePath,
|
|
292
|
-
content,
|
|
293
|
-
});
|
|
294
|
-
} catch (err) {
|
|
295
|
-
if (!opts.quiet) {
|
|
296
|
-
console.warn(` ${colors.warning}⚠${ansi.reset} Could not read file: ${filePath}`);
|
|
297
|
-
}
|
|
298
|
-
}
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
// Load diff from file if specified
|
|
302
|
-
if (opts.diffFile) {
|
|
303
|
-
try {
|
|
304
|
-
if (opts.diffFile === "-") {
|
|
305
|
-
// Read from stdin
|
|
306
|
-
payload.diff = fs.readFileSync(0, "utf-8");
|
|
307
|
-
} else {
|
|
308
|
-
payload.diff = fs.readFileSync(opts.diffFile, "utf-8");
|
|
309
|
-
}
|
|
310
|
-
} catch (err) {
|
|
311
|
-
console.error(`\n ${colors.error}✗${ansi.reset} Could not read diff file: ${opts.diffFile}\n`);
|
|
312
|
-
return EXIT.USER_ERROR;
|
|
313
|
-
}
|
|
314
|
-
}
|
|
315
|
-
|
|
316
|
-
// If no files or diff provided, try to get staged diff
|
|
317
|
-
if (payload.files.length === 0 && !payload.diff) {
|
|
318
|
-
try {
|
|
319
|
-
const { execSync } = require("child_process");
|
|
320
|
-
payload.diff = execSync("git diff --staged", {
|
|
321
|
-
cwd: projectPath,
|
|
322
|
-
encoding: "utf-8",
|
|
323
|
-
stdio: ["pipe", "pipe", "pipe"],
|
|
324
|
-
});
|
|
325
|
-
|
|
326
|
-
if (!payload.diff) {
|
|
327
|
-
// Try unstaged diff
|
|
328
|
-
payload.diff = execSync("git diff", {
|
|
329
|
-
cwd: projectPath,
|
|
330
|
-
encoding: "utf-8",
|
|
331
|
-
stdio: ["pipe", "pipe", "pipe"],
|
|
332
|
-
});
|
|
333
|
-
}
|
|
334
|
-
} catch (err) {
|
|
335
|
-
// Not a git repo or no changes
|
|
336
|
-
}
|
|
337
|
-
}
|
|
338
|
-
|
|
339
|
-
// Show info
|
|
340
|
-
if (!opts.quiet && !opts.json) {
|
|
341
|
-
console.log(`\n ${ansi.dim}Project:${ansi.reset} ${ansi.bold}${path.basename(projectPath)}${ansi.reset}`);
|
|
342
|
-
console.log(` ${ansi.dim}Authorities:${ansi.reset} ${colors.accent}${opts.authorities.join(", ")}${ansi.reset}`);
|
|
343
|
-
console.log(` ${ansi.dim}Files:${ansi.reset} ${payload.files.length}`);
|
|
344
|
-
console.log(` ${ansi.dim}Diff lines:${ansi.reset} ${payload.diff.split("\n").length}`);
|
|
345
|
-
console.log();
|
|
346
|
-
}
|
|
347
|
-
|
|
348
|
-
// Run approval
|
|
349
|
-
const spinner = new Spinner({ color: colors.primary });
|
|
350
|
-
|
|
351
|
-
if (!opts.quiet && !opts.json) {
|
|
352
|
-
spinner.start(`Requesting approval from ${opts.authorities.length} ${opts.authorities.length === 1 ? "authority" : "authorities"}...`);
|
|
353
|
-
}
|
|
354
|
-
|
|
355
|
-
let results;
|
|
356
|
-
|
|
357
|
-
try {
|
|
358
|
-
if (opts.authorities.length === 1) {
|
|
359
|
-
const result = await requestApproval(opts.authorities[0], payload);
|
|
360
|
-
results = [result];
|
|
361
|
-
} else {
|
|
362
|
-
results = await requestMultipleApprovals(opts.authorities, payload);
|
|
363
|
-
}
|
|
364
|
-
} catch (error) {
|
|
365
|
-
if (spinner) spinner.fail(`Authority review failed: ${error.message}`);
|
|
366
|
-
throw error;
|
|
367
|
-
}
|
|
368
|
-
|
|
369
|
-
if (!opts.quiet && !opts.json) {
|
|
370
|
-
spinner.succeed("Review complete");
|
|
371
|
-
}
|
|
372
|
-
|
|
373
|
-
// Get aggregated verdict for multi-authority
|
|
374
|
-
const aggregated = getAggregatedVerdict(results);
|
|
375
|
-
|
|
376
|
-
// JSON output
|
|
377
|
-
if (opts.json) {
|
|
378
|
-
const output = {
|
|
379
|
-
verdict: aggregated.verdict,
|
|
380
|
-
summary: aggregated.summary,
|
|
381
|
-
blockers: aggregated.blockers,
|
|
382
|
-
results,
|
|
383
|
-
timestamp: new Date().toISOString(),
|
|
384
|
-
};
|
|
385
|
-
console.log(JSON.stringify(output, null, 2));
|
|
386
|
-
|
|
387
|
-
// Save to file if requested
|
|
388
|
-
if (opts.output) {
|
|
389
|
-
fs.writeFileSync(opts.output, JSON.stringify(output, null, 2));
|
|
390
|
-
}
|
|
391
|
-
|
|
392
|
-
return aggregated.verdict === "APPROVED" ? 0 : aggregated.verdict === "PENDING" ? 2 : 1;
|
|
393
|
-
}
|
|
394
|
-
|
|
395
|
-
// Pretty output
|
|
396
|
-
console.log();
|
|
397
|
-
printVerdictSummary(aggregated, results);
|
|
398
|
-
|
|
399
|
-
// Print detailed findings
|
|
400
|
-
if (opts.verbose) {
|
|
401
|
-
for (const result of results) {
|
|
402
|
-
if (result.findings && result.findings.length > 0) {
|
|
403
|
-
console.log(`\n ${ansi.bold}${result.authority} Findings:${ansi.reset}\n`);
|
|
404
|
-
|
|
405
|
-
for (const finding of result.findings.slice(0, 10)) {
|
|
406
|
-
const severityIcon = finding.severity === "critical" ? colors.error + "●" :
|
|
407
|
-
finding.severity === "high" ? colors.warning + "●" :
|
|
408
|
-
finding.severity === "medium" ? colors.accent + "●" :
|
|
409
|
-
ansi.dim + "○";
|
|
410
|
-
|
|
411
|
-
console.log(` ${severityIcon}${ansi.reset} ${finding.message}`);
|
|
412
|
-
if (finding.file) {
|
|
413
|
-
console.log(` ${ansi.dim}${finding.file}${finding.line ? `:${finding.line}` : ""}${ansi.reset}`);
|
|
414
|
-
}
|
|
415
|
-
if (finding.evidence) {
|
|
416
|
-
console.log(` ${ansi.dim}${finding.evidence.slice(0, 60)}...${ansi.reset}`);
|
|
417
|
-
}
|
|
418
|
-
}
|
|
419
|
-
|
|
420
|
-
if (result.findings.length > 10) {
|
|
421
|
-
console.log(` ${ansi.dim}... and ${result.findings.length - 10} more findings${ansi.reset}`);
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
}
|
|
425
|
-
}
|
|
426
|
-
|
|
427
|
-
// Save to file if requested
|
|
428
|
-
if (opts.output) {
|
|
429
|
-
const output = {
|
|
430
|
-
verdict: aggregated.verdict,
|
|
431
|
-
summary: aggregated.summary,
|
|
432
|
-
blockers: aggregated.blockers,
|
|
433
|
-
results,
|
|
434
|
-
timestamp: new Date().toISOString(),
|
|
435
|
-
};
|
|
436
|
-
fs.writeFileSync(opts.output, JSON.stringify(output, null, 2));
|
|
437
|
-
console.log(`\n ${colors.success}✓${ansi.reset} Results saved to: ${opts.output}`);
|
|
438
|
-
}
|
|
439
|
-
|
|
440
|
-
console.log();
|
|
441
|
-
|
|
442
|
-
return aggregated.verdict === "APPROVED" ? 0 : aggregated.verdict === "PENDING" ? 2 : 1;
|
|
443
|
-
}
|
|
444
|
-
|
|
445
|
-
function printVerdictSummary(aggregated, results) {
|
|
446
|
-
const verdictSymbol = aggregated.verdict === "APPROVED" ? colors.success + "✓" :
|
|
447
|
-
aggregated.verdict === "PENDING" ? colors.warning + "○" :
|
|
448
|
-
colors.error + "✗";
|
|
449
|
-
|
|
450
|
-
const verdictColor = aggregated.verdict === "APPROVED" ? colors.success :
|
|
451
|
-
aggregated.verdict === "PENDING" ? colors.warning :
|
|
452
|
-
colors.error;
|
|
453
|
-
|
|
454
|
-
console.log(" ┌────────────────────────────────────────────────────────────────────┐");
|
|
455
|
-
console.log(` │ ${verdictSymbol}${ansi.reset} Verdict: ${verdictColor}${ansi.bold}${aggregated.verdict}${ansi.reset} │`);
|
|
456
|
-
console.log(" ├────────────────────────────────────────────────────────────────────┤");
|
|
457
|
-
|
|
458
|
-
// Summary line
|
|
459
|
-
const { approved, rejected, pending, error } = aggregated.summary;
|
|
460
|
-
const parts = [];
|
|
461
|
-
if (approved > 0) parts.push(`${colors.success}${approved} approved${ansi.reset}`);
|
|
462
|
-
if (rejected > 0) parts.push(`${colors.error}${rejected} rejected${ansi.reset}`);
|
|
463
|
-
if (pending > 0) parts.push(`${colors.warning}${pending} pending${ansi.reset}`);
|
|
464
|
-
if (error > 0) parts.push(`${colors.error}${error} error${ansi.reset}`);
|
|
465
|
-
|
|
466
|
-
console.log(` │ ${parts.join(" ")}`.padEnd(75) + "│");
|
|
467
|
-
console.log(" └────────────────────────────────────────────────────────────────────┘");
|
|
468
|
-
|
|
469
|
-
// Individual results
|
|
470
|
-
console.log(`\n ${ansi.bold}Authority Results:${ansi.reset}\n`);
|
|
471
|
-
|
|
472
|
-
for (const result of results) {
|
|
473
|
-
const resultSymbol = result.verdict === "APPROVED" ? colors.success + "✓" :
|
|
474
|
-
result.verdict === "PENDING" ? colors.warning + "○" :
|
|
475
|
-
colors.error + "✗";
|
|
476
|
-
|
|
477
|
-
const findingsCount = result.findings ? result.findings.length : 0;
|
|
478
|
-
const findingsStr = findingsCount > 0 ? `${ansi.dim}(${findingsCount} findings)${ansi.reset}` : "";
|
|
479
|
-
|
|
480
|
-
console.log(` ${resultSymbol}${ansi.reset} ${colors.accent}${result.authority}${ansi.reset}: ${result.verdict} ${findingsStr}`);
|
|
481
|
-
console.log(` ${ansi.dim}${result.reason}${ansi.reset}`);
|
|
482
|
-
|
|
483
|
-
if (result.qualityScore !== undefined) {
|
|
484
|
-
console.log(` ${ansi.dim}Quality Score: ${result.qualityScore}/100${ansi.reset}`);
|
|
485
|
-
}
|
|
486
|
-
}
|
|
487
|
-
|
|
488
|
-
// Blockers
|
|
489
|
-
if (aggregated.blockers.length > 0) {
|
|
490
|
-
console.log(`\n ${ansi.bold}Blockers:${ansi.reset}\n`);
|
|
491
|
-
for (const blocker of aggregated.blockers) {
|
|
492
|
-
console.log(` ${colors.error}•${ansi.reset} ${blocker}`);
|
|
493
|
-
}
|
|
494
|
-
}
|
|
495
|
-
}
|
|
496
|
-
|
|
497
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
498
|
-
// MAIN COMMAND
|
|
499
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
500
|
-
|
|
501
|
-
async function runAuthority(args) {
|
|
502
|
-
const opts = parseArgs(args);
|
|
503
|
-
|
|
504
|
-
// Show help
|
|
505
|
-
if (opts.help) {
|
|
506
|
-
printHelp(shouldShowBanner(opts));
|
|
507
|
-
return 0;
|
|
508
|
-
}
|
|
509
|
-
|
|
510
|
-
// Print banner
|
|
511
|
-
if (shouldShowBanner(opts) && !opts.json) {
|
|
512
|
-
printBanner();
|
|
513
|
-
}
|
|
514
|
-
|
|
515
|
-
// Route to subcommand
|
|
516
|
-
switch (opts.subcommand) {
|
|
517
|
-
case "list":
|
|
518
|
-
return await runAuthorityList(opts);
|
|
519
|
-
case "approve":
|
|
520
|
-
return await runAuthorityApprove(opts);
|
|
521
|
-
default:
|
|
522
|
-
return await runAuthorityList(opts);
|
|
523
|
-
}
|
|
524
|
-
}
|
|
525
|
-
|
|
526
|
-
module.exports = {
|
|
527
|
-
runAuthority: withErrorHandling(runAuthority, "Authority command failed"),
|
|
528
|
-
};
|