@vibecheckai/cli 3.5.1 → 3.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/bin/registry.js +406 -154
- package/bin/runners/context/analyzer.js +52 -1
- package/bin/runners/context/generators/mcp.js +15 -13
- package/bin/runners/context/git-context.js +3 -1
- package/bin/runners/context/proof-context.js +248 -1
- package/bin/runners/context/team-conventions.js +33 -7
- package/bin/runners/lib/agent-firewall/ai/false-positive-analyzer.js +474 -0
- package/bin/runners/lib/agent-firewall/change-packet/builder.js +488 -0
- package/bin/runners/lib/agent-firewall/change-packet/schema.json +228 -0
- package/bin/runners/lib/agent-firewall/change-packet/store.js +200 -0
- package/bin/runners/lib/agent-firewall/claims/claim-types.js +21 -0
- package/bin/runners/lib/agent-firewall/claims/extractor.js +303 -0
- package/bin/runners/lib/agent-firewall/claims/patterns.js +24 -0
- package/bin/runners/lib/agent-firewall/critic/index.js +151 -0
- package/bin/runners/lib/agent-firewall/critic/judge.js +432 -0
- package/bin/runners/lib/agent-firewall/critic/prompts.js +305 -0
- package/bin/runners/lib/agent-firewall/evidence/auth-evidence.js +88 -0
- package/bin/runners/lib/agent-firewall/evidence/contract-evidence.js +75 -0
- package/bin/runners/lib/agent-firewall/evidence/env-evidence.js +127 -0
- package/bin/runners/lib/agent-firewall/evidence/resolver.js +102 -0
- package/bin/runners/lib/agent-firewall/evidence/route-evidence.js +213 -0
- package/bin/runners/lib/agent-firewall/evidence/side-effect-evidence.js +145 -0
- package/bin/runners/lib/agent-firewall/fs-hook/daemon.js +19 -0
- package/bin/runners/lib/agent-firewall/fs-hook/installer.js +87 -0
- package/bin/runners/lib/agent-firewall/fs-hook/watcher.js +184 -0
- package/bin/runners/lib/agent-firewall/git-hook/pre-commit.js +163 -0
- package/bin/runners/lib/agent-firewall/ide-extension/cursor.js +107 -0
- package/bin/runners/lib/agent-firewall/ide-extension/vscode.js +68 -0
- package/bin/runners/lib/agent-firewall/ide-extension/windsurf.js +66 -0
- package/bin/runners/lib/agent-firewall/interceptor/base.js +304 -0
- package/bin/runners/lib/agent-firewall/interceptor/cursor.js +35 -0
- package/bin/runners/lib/agent-firewall/interceptor/vscode.js +35 -0
- package/bin/runners/lib/agent-firewall/interceptor/windsurf.js +34 -0
- package/bin/runners/lib/agent-firewall/lawbook/distributor.js +465 -0
- package/bin/runners/lib/agent-firewall/lawbook/evaluator.js +604 -0
- package/bin/runners/lib/agent-firewall/lawbook/index.js +304 -0
- package/bin/runners/lib/agent-firewall/lawbook/registry.js +514 -0
- package/bin/runners/lib/agent-firewall/lawbook/schema.js +420 -0
- package/bin/runners/lib/agent-firewall/logger.js +141 -0
- package/bin/runners/lib/agent-firewall/policy/default-policy.json +90 -0
- package/bin/runners/lib/agent-firewall/policy/engine.js +103 -0
- package/bin/runners/lib/agent-firewall/policy/loader.js +451 -0
- package/bin/runners/lib/agent-firewall/policy/rules/auth-drift.js +50 -0
- package/bin/runners/lib/agent-firewall/policy/rules/contract-drift.js +50 -0
- package/bin/runners/lib/agent-firewall/policy/rules/fake-success.js +86 -0
- package/bin/runners/lib/agent-firewall/policy/rules/ghost-env.js +162 -0
- package/bin/runners/lib/agent-firewall/policy/rules/ghost-route.js +189 -0
- package/bin/runners/lib/agent-firewall/policy/rules/scope.js +93 -0
- package/bin/runners/lib/agent-firewall/policy/rules/unsafe-side-effect.js +57 -0
- package/bin/runners/lib/agent-firewall/policy/schema.json +183 -0
- package/bin/runners/lib/agent-firewall/policy/verdict.js +54 -0
- package/bin/runners/lib/agent-firewall/proposal/extractor.js +394 -0
- package/bin/runners/lib/agent-firewall/proposal/index.js +212 -0
- package/bin/runners/lib/agent-firewall/proposal/schema.js +251 -0
- package/bin/runners/lib/agent-firewall/proposal/validator.js +386 -0
- package/bin/runners/lib/agent-firewall/reality/index.js +332 -0
- package/bin/runners/lib/agent-firewall/reality/state.js +625 -0
- package/bin/runners/lib/agent-firewall/reality/watcher.js +322 -0
- package/bin/runners/lib/agent-firewall/risk/index.js +173 -0
- package/bin/runners/lib/agent-firewall/risk/scorer.js +328 -0
- package/bin/runners/lib/agent-firewall/risk/thresholds.js +321 -0
- package/bin/runners/lib/agent-firewall/risk/vectors.js +421 -0
- package/bin/runners/lib/agent-firewall/simulator/diff-simulator.js +472 -0
- package/bin/runners/lib/agent-firewall/simulator/import-resolver.js +346 -0
- package/bin/runners/lib/agent-firewall/simulator/index.js +181 -0
- package/bin/runners/lib/agent-firewall/simulator/route-validator.js +380 -0
- package/bin/runners/lib/agent-firewall/time-machine/incident-correlator.js +661 -0
- package/bin/runners/lib/agent-firewall/time-machine/index.js +267 -0
- package/bin/runners/lib/agent-firewall/time-machine/replay-engine.js +436 -0
- package/bin/runners/lib/agent-firewall/time-machine/state-reconstructor.js +490 -0
- package/bin/runners/lib/agent-firewall/time-machine/timeline-builder.js +530 -0
- package/bin/runners/lib/agent-firewall/truthpack/index.js +67 -0
- package/bin/runners/lib/agent-firewall/truthpack/loader.js +137 -0
- package/bin/runners/lib/agent-firewall/unblock/planner.js +337 -0
- package/bin/runners/lib/agent-firewall/utils/ignore-checker.js +118 -0
- package/bin/runners/lib/analysis-core.js +220 -182
- package/bin/runners/lib/analyzers.js +2145 -224
- package/bin/runners/lib/api-client.js +269 -0
- package/bin/runners/lib/authority-badge.js +425 -0
- package/bin/runners/lib/cli-output.js +242 -210
- package/bin/runners/lib/default-config.js +127 -0
- package/bin/runners/lib/detectors-v2.js +547 -785
- 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 +190 -0
- package/bin/runners/lib/engines/api-consistency-engine.js +162 -0
- package/bin/runners/lib/engines/ast-cache.js +99 -0
- package/bin/runners/lib/engines/code-quality-engine.js +255 -0
- package/bin/runners/lib/engines/console-logs-engine.js +115 -0
- package/bin/runners/lib/engines/cross-file-analysis-engine.js +268 -0
- package/bin/runners/lib/engines/dead-code-engine.js +198 -0
- package/bin/runners/lib/engines/deprecated-api-engine.js +226 -0
- package/bin/runners/lib/engines/empty-catch-engine.js +150 -0
- package/bin/runners/lib/engines/file-filter.js +131 -0
- package/bin/runners/lib/engines/hardcoded-secrets-engine.js +251 -0
- package/bin/runners/lib/engines/mock-data-engine.js +272 -0
- package/bin/runners/lib/engines/parallel-processor.js +71 -0
- package/bin/runners/lib/engines/performance-issues-engine.js +265 -0
- package/bin/runners/lib/engines/security-vulnerabilities-engine.js +243 -0
- package/bin/runners/lib/engines/todo-fixme-engine.js +115 -0
- package/bin/runners/lib/engines/type-aware-engine.js +152 -0
- package/bin/runners/lib/engines/unsafe-regex-engine.js +225 -0
- package/bin/runners/lib/engines/vibecheck-engines/README.md +53 -0
- package/bin/runners/lib/engines/vibecheck-engines/index.js +15 -0
- 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 +139 -0
- 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/engines/vibecheck-engines/package.json +13 -0
- package/bin/runners/lib/entitlements-v2.js +152 -446
- package/bin/runners/lib/error-handler.js +60 -12
- package/bin/runners/lib/error-messages.js +289 -0
- package/bin/runners/lib/evidence-pack.js +7 -1
- package/bin/runners/lib/exit-codes.js +275 -0
- package/bin/runners/lib/finding-id.js +69 -0
- package/bin/runners/lib/finding-sorter.js +89 -0
- package/bin/runners/lib/fingerprint.js +377 -0
- package/bin/runners/lib/global-flags.js +37 -0
- package/bin/runners/lib/help-formatter.js +413 -0
- package/bin/runners/lib/logger.js +38 -0
- 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/route-truth.js +1167 -322
- package/bin/runners/lib/scan-output.js +504 -463
- 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 +239 -0
- package/bin/runners/lib/ship-output.js +328 -31
- package/bin/runners/lib/terminal-ui.js +234 -731
- package/bin/runners/lib/truth.js +1332 -308
- package/bin/runners/lib/unified-cli-output.js +604 -0
- package/bin/runners/lib/unified-output.js +163 -155
- package/bin/runners/lib/upsell.js +104 -204
- package/bin/runners/runAgent.d.ts +5 -0
- package/bin/runners/runAgent.js +161 -0
- package/bin/runners/runAllowlist.js +166 -101
- package/bin/runners/runApprove.js +1200 -0
- package/bin/runners/runAuth.js +373 -95
- package/bin/runners/runCheckpoint.js +59 -21
- package/bin/runners/runClassify.js +926 -0
- package/bin/runners/runContext.d.ts +4 -0
- package/bin/runners/runContext.js +136 -24
- package/bin/runners/runDoctor.js +115 -67
- package/bin/runners/runEvidencePack.js +239 -96
- package/bin/runners/runFirewall.d.ts +5 -0
- package/bin/runners/runFirewall.js +134 -0
- package/bin/runners/runFirewallHook.d.ts +5 -0
- package/bin/runners/runFirewallHook.js +56 -0
- package/bin/runners/runFix.js +6 -5
- package/bin/runners/runGuard.js +212 -118
- package/bin/runners/runInit.js +66 -21
- package/bin/runners/runLabs.js +204 -121
- package/bin/runners/runMcp.js +131 -60
- package/bin/runners/runPolish.d.ts +4 -0
- package/bin/runners/runPolish.js +43 -20
- package/bin/runners/runProof.zip +0 -0
- package/bin/runners/runProve.js +15 -5
- package/bin/runners/runQuickstart.js +531 -0
- package/bin/runners/runReality.js +14 -0
- package/bin/runners/runReport.js +36 -4
- package/bin/runners/runScan.js +689 -91
- package/bin/runners/runShip.js +96 -40
- package/bin/runners/runTruth.d.ts +5 -0
- package/bin/runners/runTruth.js +101 -0
- package/bin/runners/runValidate.js +21 -4
- package/bin/runners/runWatch.js +118 -54
- package/bin/scan.js +6 -1
- package/bin/vibecheck.js +297 -52
- package/mcp-server/HARDENING_SUMMARY.md +299 -0
- package/mcp-server/agent-firewall-interceptor.js +500 -0
- package/mcp-server/authority-tools.js +569 -0
- package/mcp-server/conductor/conflict-resolver.js +588 -0
- package/mcp-server/conductor/execution-planner.js +544 -0
- package/mcp-server/conductor/index.js +377 -0
- package/mcp-server/conductor/lock-manager.js +615 -0
- package/mcp-server/conductor/request-queue.js +550 -0
- package/mcp-server/conductor/session-manager.js +500 -0
- package/mcp-server/conductor/tools.js +510 -0
- package/mcp-server/deprecation-middleware.js +282 -0
- package/mcp-server/handlers/index.ts +15 -0
- package/mcp-server/handlers/tool-handler.ts +474 -591
- package/mcp-server/index.js +1748 -1099
- package/mcp-server/lib/api-client.cjs +13 -0
- package/mcp-server/lib/cache-wrapper.cjs +383 -0
- package/mcp-server/lib/error-envelope.js +138 -0
- package/mcp-server/lib/executor.ts +428 -721
- package/mcp-server/lib/index.ts +19 -0
- package/mcp-server/lib/logger.cjs +30 -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 +342 -284
- package/mcp-server/lib/types.ts +267 -0
- package/mcp-server/logger.js +173 -0
- package/mcp-server/package.json +11 -27
- package/mcp-server/premium-tools.js +2 -2
- package/mcp-server/registry/tool-registry.js +794 -0
- package/mcp-server/registry/tools.json +507 -378
- package/mcp-server/registry.test.ts +334 -0
- package/mcp-server/tests/tier-gating.test.js +297 -0
- package/mcp-server/tier-auth.js +492 -347
- package/mcp-server/tools-v3.js +950 -0
- package/mcp-server/truth-context.js +131 -90
- package/mcp-server/truth-firewall-tools.js +1612 -1001
- package/mcp-server/tsconfig.json +8 -5
- package/mcp-server/vibecheck-2.0-tools.js +14 -1
- package/mcp-server/vibecheck-mcp-server-3.2.0.tgz +0 -0
- package/mcp-server/vibecheck-tools.js +2 -2
- package/package.json +4 -3
- package/bin/runners/runInstall.js +0 -281
- package/mcp-server/ARCHITECTURE.md +0 -339
- package/mcp-server/__tests__/cache.test.ts +0 -313
- package/mcp-server/__tests__/executor.test.ts +0 -239
- package/mcp-server/__tests__/fixtures/exclusion-test/.cache/webpack/cache.pack +0 -1
- package/mcp-server/__tests__/fixtures/exclusion-test/.next/server/chunk.js +0 -3
- package/mcp-server/__tests__/fixtures/exclusion-test/.turbo/cache.json +0 -3
- package/mcp-server/__tests__/fixtures/exclusion-test/.venv/lib/env.py +0 -3
- package/mcp-server/__tests__/fixtures/exclusion-test/dist/bundle.js +0 -3
- package/mcp-server/__tests__/fixtures/exclusion-test/package.json +0 -5
- package/mcp-server/__tests__/fixtures/exclusion-test/src/app.ts +0 -5
- package/mcp-server/__tests__/fixtures/exclusion-test/venv/lib/config.py +0 -4
- package/mcp-server/__tests__/ids.test.ts +0 -345
- package/mcp-server/__tests__/integration/tools.test.ts +0 -410
- package/mcp-server/__tests__/registry.test.ts +0 -365
- package/mcp-server/__tests__/sandbox.test.ts +0 -323
- package/mcp-server/__tests__/schemas.test.ts +0 -372
- package/mcp-server/benchmarks/run-benchmarks.ts +0 -304
- package/mcp-server/examples/doctor.request.json +0 -14
- package/mcp-server/examples/doctor.response.json +0 -53
- package/mcp-server/examples/error.response.json +0 -15
- package/mcp-server/examples/scan.request.json +0 -14
- package/mcp-server/examples/scan.response.json +0 -108
- package/mcp-server/index-v3.ts +0 -293
- package/mcp-server/index.old.js +0 -4137
- package/mcp-server/lib/cache.ts +0 -341
- package/mcp-server/lib/errors.ts +0 -346
- package/mcp-server/lib/ids.ts +0 -238
- package/mcp-server/lib/logger.ts +0 -368
- package/mcp-server/lib/metrics.ts +0 -365
- package/mcp-server/lib/validator.ts +0 -229
- package/mcp-server/package-lock.json +0 -165
- package/mcp-server/schemas/error-envelope.schema.json +0 -125
- package/mcp-server/schemas/finding.schema.json +0 -167
- package/mcp-server/schemas/report-artifact.schema.json +0 -88
- package/mcp-server/schemas/run-request.schema.json +0 -75
- package/mcp-server/schemas/verdict.schema.json +0 -168
- package/mcp-server/tier-auth.d.ts +0 -71
- package/mcp-server/vitest.config.ts +0 -16
|
@@ -1,25 +1,9 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Entitlements
|
|
2
|
+
* VibeCheck Entitlements
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
7
|
-
* NO BYPASS ALLOWED:
|
|
8
|
-
* - No owner-mode env vars
|
|
9
|
-
* - No offline fallback that grants paid features
|
|
10
|
-
* - No silent feature access
|
|
11
|
-
*
|
|
12
|
-
* Exit Codes:
|
|
13
|
-
* - 0: Success
|
|
14
|
-
* - 2: BLOCK verdict (CI failure)
|
|
15
|
-
* - 3: Feature not allowed (upgrade required)
|
|
16
|
-
* - 4: Misconfiguration/env error
|
|
17
|
-
*
|
|
18
|
-
* Tiers:
|
|
19
|
-
* - FREE ($0): Basic scanning and validation
|
|
20
|
-
* - STARTER ($39/repo/mo): CI/CD gates, PR checks, badges, MCP
|
|
21
|
-
* - PRO ($99/repo/mo): Full fix, prove, ai-test, share, advanced reality, permissions, graph, patch apply
|
|
22
|
-
* - COMPLIANCE (Enterprise): Advanced compliance packs, audit trails
|
|
4
|
+
* Simple 2-tier model:
|
|
5
|
+
* - FREE ($0): Inspect & Observe
|
|
6
|
+
* - PRO ($69/mo): Fix, Prove & Enforce
|
|
23
7
|
*/
|
|
24
8
|
|
|
25
9
|
"use strict";
|
|
@@ -27,254 +11,120 @@
|
|
|
27
11
|
const fs = require("fs");
|
|
28
12
|
const path = require("path");
|
|
29
13
|
const os = require("os");
|
|
30
|
-
const crypto = require("crypto");
|
|
31
14
|
|
|
32
|
-
//
|
|
15
|
+
// ============================================================================
|
|
33
16
|
// EXIT CODES
|
|
34
|
-
//
|
|
17
|
+
// ============================================================================
|
|
35
18
|
const EXIT_SUCCESS = 0;
|
|
36
|
-
const EXIT_BLOCK_VERDICT = 2;
|
|
37
19
|
const EXIT_FEATURE_NOT_ALLOWED = 3;
|
|
38
|
-
const EXIT_MISCONFIG = 4;
|
|
39
20
|
|
|
40
|
-
//
|
|
41
|
-
//
|
|
42
|
-
//
|
|
21
|
+
// ============================================================================
|
|
22
|
+
// TIERS
|
|
23
|
+
// ============================================================================
|
|
43
24
|
const TIERS = {
|
|
44
|
-
free: { name: "FREE", price: 0
|
|
45
|
-
|
|
46
|
-
pro: { name: "PRO", price: 99, order: 2 },
|
|
47
|
-
compliance: { name: "COMPLIANCE", price: 0, order: 3 }, // Enterprise/on-prem
|
|
48
|
-
};
|
|
49
|
-
|
|
50
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
51
|
-
// ENTITLEMENTS MATRIX - SOURCE OF TRUTH
|
|
52
|
-
// Format: feature -> { minTier, caps?, downgrade? }
|
|
53
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
54
|
-
const ENTITLEMENTS = {
|
|
55
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
56
|
-
// CORE COMMANDS
|
|
57
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
58
|
-
"scan": { minTier: "free" },
|
|
59
|
-
"scan.autofix": { minTier: "starter" }, // Apply safe fixes + missions
|
|
60
|
-
"ship": { minTier: "free", caps: { free: "static-only" } },
|
|
61
|
-
"ship.static": { minTier: "free" },
|
|
62
|
-
"ship.full": { minTier: "pro" },
|
|
63
|
-
|
|
64
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
65
|
-
// INIT MODES
|
|
66
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
67
|
-
"init": { minTier: "free" },
|
|
68
|
-
"init.local": { minTier: "free" }, // Full local setup
|
|
69
|
-
"init.connect": { minTier: "starter" }, // GitHub Actions + PR comments
|
|
70
|
-
|
|
71
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
72
|
-
// CHECKPOINT
|
|
73
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
74
|
-
"checkpoint": { minTier: "free", downgrade: "checkpoint.basic" },
|
|
75
|
-
"checkpoint.basic": { minTier: "free" }, // Basic diff comparison
|
|
76
|
-
"checkpoint.hallucination": { minTier: "pro" }, // Hallucination scoring
|
|
77
|
-
|
|
78
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
79
|
-
// REALITY TESTING
|
|
80
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
81
|
-
"reality": { minTier: "free", downgrade: "reality.preview" },
|
|
82
|
-
"reality.preview": { minTier: "free", caps: { free: { maxPages: 5, maxClicks: 20, noAuthBoundary: true } } },
|
|
83
|
-
"reality.basic": { minTier: "starter", caps: { starter: { maxPages: 50, maxClicks: 200, basicAuthVerify: true } } },
|
|
84
|
-
"reality.full": { minTier: "pro" },
|
|
85
|
-
"reality.advanced_auth_boundary": { minTier: "pro" },
|
|
86
|
-
|
|
87
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
88
|
-
// PROVE COMMAND
|
|
89
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
90
|
-
"prove": { minTier: "pro" },
|
|
91
|
-
|
|
92
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
93
|
-
// FIX COMMAND
|
|
94
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
95
|
-
"fix": { minTier: "free", downgrade: "fix.plan_only" },
|
|
96
|
-
"fix.plan_only": { minTier: "free" }, // Generate missions, don't apply
|
|
97
|
-
"fix.apply_patches": { minTier: "pro" }, // Apply patches automatically
|
|
98
|
-
"fix.loop": { minTier: "pro" }, // Continuous fix loop
|
|
99
|
-
|
|
100
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
101
|
-
// REPORT FORMATS
|
|
102
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
103
|
-
"report": { minTier: "free", downgrade: "report.html_md" },
|
|
104
|
-
"report.html_md": { minTier: "free" },
|
|
105
|
-
"report.sarif_csv": { minTier: "starter" }, // SARIF/CSV at STARTER
|
|
106
|
-
"report.compliance_packs": { minTier: "compliance" },
|
|
107
|
-
|
|
108
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
109
|
-
// SETUP & DX
|
|
110
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
111
|
-
"install": { minTier: "free" },
|
|
112
|
-
"doctor": { minTier: "free" },
|
|
113
|
-
"status": { minTier: "free" },
|
|
114
|
-
"watch": { minTier: "free", downgrade: "watch.local" },
|
|
115
|
-
"watch.local": { minTier: "free" }, // Local-only file watching
|
|
116
|
-
"watch.pr": { minTier: "starter" }, // PR updates on changes
|
|
117
|
-
"preflight": { minTier: "free" },
|
|
118
|
-
"polish": { minTier: "free" },
|
|
119
|
-
|
|
120
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
121
|
-
// AI TRUTH
|
|
122
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
123
|
-
"ctx": { minTier: "free" },
|
|
124
|
-
"guard": { minTier: "free" },
|
|
125
|
-
"context": { minTier: "free" },
|
|
126
|
-
"mdc": { minTier: "free" },
|
|
127
|
-
"contracts": { minTier: "free" },
|
|
128
|
-
|
|
129
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
130
|
-
// EXPORT COMMAND (subcommands gate individually)
|
|
131
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
132
|
-
"export": { minTier: "free" }, // Base export command is free, subcommands gate themselves
|
|
133
|
-
|
|
134
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
135
|
-
// RUNTIME COMMAND (browser-based verification)
|
|
136
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
137
|
-
"runtime": { minTier: "free", downgrade: "reality.preview" }, // Same as reality
|
|
138
|
-
|
|
139
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
140
|
-
// SECURITY COMMAND (AuthZ & IDOR)
|
|
141
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
142
|
-
"security": { minTier: "pro" },
|
|
143
|
-
|
|
144
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
145
|
-
// PRO ONLY
|
|
146
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
147
|
-
"replay": { minTier: "pro" },
|
|
148
|
-
"share": { minTier: "pro" },
|
|
149
|
-
"ai-test": { minTier: "pro" },
|
|
150
|
-
"permissions": { minTier: "pro" },
|
|
151
|
-
"graph": { minTier: "pro" },
|
|
152
|
-
|
|
153
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
154
|
-
// STARTER AND ABOVE
|
|
155
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
156
|
-
"gate": { minTier: "starter" },
|
|
157
|
-
"pr": { minTier: "starter" },
|
|
158
|
-
"badge": { minTier: "starter" },
|
|
159
|
-
"launch": { minTier: "starter" },
|
|
160
|
-
"dashboard_sync": { minTier: "starter" },
|
|
161
|
-
|
|
162
|
-
// MCP Server
|
|
163
|
-
"mcp": { minTier: "starter", downgrade: "mcp.help_only" },
|
|
164
|
-
"mcp.help_only": { minTier: "free", caps: { free: "help and print-config only" } },
|
|
165
|
-
"mcp.read_only": { minTier: "starter", caps: { starter: "read-only safe tools, rate limited" } },
|
|
166
|
-
"mcp.full": { minTier: "pro", caps: { pro: "full tools, audit logs, higher limits" } },
|
|
167
|
-
|
|
168
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
169
|
-
// ACCOUNT (ALWAYS FREE)
|
|
170
|
-
// ─────────────────────────────────────────────────────────────────────────────
|
|
171
|
-
"login": { minTier: "free" },
|
|
172
|
-
"logout": { minTier: "free" },
|
|
173
|
-
"whoami": { minTier: "free" },
|
|
174
|
-
|
|
175
|
-
// Labs/experimental
|
|
176
|
-
"labs": { minTier: "free" },
|
|
25
|
+
free: { name: "FREE", price: 0 },
|
|
26
|
+
pro: { name: "PRO", price: 69 },
|
|
177
27
|
};
|
|
178
28
|
|
|
179
|
-
//
|
|
180
|
-
//
|
|
181
|
-
//
|
|
182
|
-
const
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
fixApplyPatches: false,
|
|
199
|
-
scansPerMonth: 500,
|
|
200
|
-
shipChecksPerMonth: 200,
|
|
201
|
-
},
|
|
202
|
-
pro: {
|
|
203
|
-
realityMaxPages: -1, // unlimited
|
|
204
|
-
realityMaxClicks: -1,
|
|
205
|
-
realityAuthBoundary: true,
|
|
206
|
-
realityAdvancedAuth: true,
|
|
207
|
-
reportFormats: ["html", "md", "sarif", "csv"],
|
|
208
|
-
fixApplyPatches: true,
|
|
209
|
-
scansPerMonth: -1, // unlimited
|
|
210
|
-
shipChecksPerMonth: -1,
|
|
211
|
-
},
|
|
212
|
-
compliance: {
|
|
213
|
-
realityMaxPages: -1,
|
|
214
|
-
realityMaxClicks: -1,
|
|
215
|
-
realityAuthBoundary: true,
|
|
216
|
-
realityAdvancedAuth: true,
|
|
217
|
-
reportFormats: ["html", "md", "sarif", "csv", "compliance"],
|
|
218
|
-
fixApplyPatches: true,
|
|
219
|
-
scansPerMonth: -1,
|
|
220
|
-
shipChecksPerMonth: -1,
|
|
221
|
-
},
|
|
222
|
-
};
|
|
29
|
+
// ============================================================================
|
|
30
|
+
// GATED FEATURES
|
|
31
|
+
// ============================================================================
|
|
32
|
+
const FREE_FEATURES = [
|
|
33
|
+
// Setup & environment
|
|
34
|
+
"init", "doctor", "install", "status", "watch", "preflight",
|
|
35
|
+
// Scan & analysis
|
|
36
|
+
"scan", "runtime",
|
|
37
|
+
// AI verification
|
|
38
|
+
"ctx", "contracts", "verify",
|
|
39
|
+
// Reports
|
|
40
|
+
"report", "export",
|
|
41
|
+
// Account
|
|
42
|
+
"login", "logout", "whoami",
|
|
43
|
+
// Preview modes
|
|
44
|
+
"reality.preview", "firewall.observe",
|
|
45
|
+
// Misc
|
|
46
|
+
"labs", "mdc",
|
|
47
|
+
];
|
|
223
48
|
|
|
224
|
-
const
|
|
49
|
+
const PRO_FEATURES = [
|
|
50
|
+
// CI/CD & PR
|
|
51
|
+
"gate", "pr", "badge", "ship",
|
|
52
|
+
// Fixes
|
|
53
|
+
"fix", "fix.apply", "fix.analyze", "fix.diff", "fix.rules", "scan.autofix",
|
|
54
|
+
// Prove & verify
|
|
55
|
+
"prove", "replay", "permissions", "graph", "ai-test", "share",
|
|
56
|
+
// Advanced
|
|
57
|
+
"checkpoint", "polish", "guard", "context",
|
|
58
|
+
// Full modes
|
|
59
|
+
"firewall.enforce", "reality.full", "mcp.full",
|
|
60
|
+
// All FREE features
|
|
61
|
+
...FREE_FEATURES,
|
|
62
|
+
];
|
|
225
63
|
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
64
|
+
/**
|
|
65
|
+
* Check if developer mode bypass is allowed.
|
|
66
|
+
*
|
|
67
|
+
* SECURITY: VIBECHECK_DEV_PRO is ONLY allowed in non-production environments.
|
|
68
|
+
* This prevents environment variable injection from granting PRO access in production.
|
|
69
|
+
*
|
|
70
|
+
* @returns {boolean} True only if in development AND VIBECHECK_DEV_PRO=1
|
|
71
|
+
*/
|
|
72
|
+
function isDevProBypassAllowed() {
|
|
73
|
+
// SECURITY: Never allow dev bypass in production
|
|
74
|
+
if (process.env.NODE_ENV === "production") {
|
|
75
|
+
return false;
|
|
76
|
+
}
|
|
77
|
+
// Also block in CI environments to prevent pipeline exploitation
|
|
78
|
+
if (process.env.CI === "true" || process.env.CI === "1") {
|
|
79
|
+
return false;
|
|
237
80
|
}
|
|
238
|
-
return
|
|
81
|
+
return process.env.VIBECHECK_DEV_PRO === "1";
|
|
239
82
|
}
|
|
240
83
|
|
|
241
|
-
|
|
242
|
-
//
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
const current = TIERS[currentTier]?.order ?? -1;
|
|
246
|
-
const required = TIERS[requiredTier]?.order ?? 999;
|
|
247
|
-
return current >= required;
|
|
84
|
+
function isPro(tier) {
|
|
85
|
+
// Developer mode bypass (blocked in production)
|
|
86
|
+
if (isDevProBypassAllowed()) return true;
|
|
87
|
+
return tier === "pro";
|
|
248
88
|
}
|
|
249
89
|
|
|
250
|
-
function
|
|
251
|
-
|
|
90
|
+
function tierHasFeature(tier, feature) {
|
|
91
|
+
// Developer mode bypass - grant all features (blocked in production)
|
|
92
|
+
if (isDevProBypassAllowed()) return true;
|
|
93
|
+
if (tier === "pro") return true; // PRO has everything
|
|
94
|
+
return FREE_FEATURES.includes(feature);
|
|
252
95
|
}
|
|
253
96
|
|
|
254
|
-
//
|
|
255
|
-
//
|
|
256
|
-
//
|
|
97
|
+
// ============================================================================
|
|
98
|
+
// API
|
|
99
|
+
// ============================================================================
|
|
100
|
+
const API_BASE_URL = process.env.VIBECHECK_API_URL || "https://api.vibecheckai.dev";
|
|
101
|
+
|
|
257
102
|
let _cachedTier = null;
|
|
258
103
|
let _cachedTierExpiry = 0;
|
|
259
104
|
|
|
260
105
|
async function getTier(options = {}) {
|
|
261
|
-
const { apiKey,
|
|
106
|
+
const { apiKey, forceRefresh = false } = options;
|
|
107
|
+
|
|
108
|
+
// Developer mode: VIBECHECK_DEV_PRO=1 grants pro tier for local development
|
|
109
|
+
// SECURITY: This bypass is blocked in production environments
|
|
110
|
+
if (isDevProBypassAllowed()) {
|
|
111
|
+
_cachedTier = "pro";
|
|
112
|
+
_cachedTierExpiry = Date.now() + 86400000; // 24 hours
|
|
113
|
+
return "pro";
|
|
114
|
+
}
|
|
262
115
|
|
|
263
|
-
// Check cache (5 minute TTL)
|
|
264
116
|
if (!forceRefresh && _cachedTier && Date.now() < _cachedTierExpiry) {
|
|
265
117
|
return _cachedTier;
|
|
266
118
|
}
|
|
267
119
|
|
|
268
|
-
// No API key = free tier
|
|
269
120
|
if (!apiKey) {
|
|
270
121
|
_cachedTier = "free";
|
|
271
122
|
_cachedTierExpiry = Date.now() + 300000;
|
|
272
123
|
return "free";
|
|
273
124
|
}
|
|
274
125
|
|
|
275
|
-
// Fetch from API
|
|
276
126
|
try {
|
|
277
|
-
const res = await fetch(`${API_BASE_URL}/v1/
|
|
127
|
+
const res = await fetch(`${API_BASE_URL}/v1/auth/whoami`, {
|
|
278
128
|
method: "GET",
|
|
279
129
|
headers: { "Authorization": `Bearer ${apiKey}` },
|
|
280
130
|
signal: AbortSignal.timeout(5000),
|
|
@@ -282,113 +132,33 @@ async function getTier(options = {}) {
|
|
|
282
132
|
|
|
283
133
|
if (res.ok) {
|
|
284
134
|
const data = await res.json();
|
|
285
|
-
|
|
135
|
+
// Map any paid tier to 'pro'
|
|
136
|
+
const plan = data.plan || data.tier || "free";
|
|
137
|
+
_cachedTier = (plan === "free") ? "free" : "pro";
|
|
286
138
|
_cachedTierExpiry = Date.now() + 300000;
|
|
287
|
-
|
|
288
|
-
// Cache locally
|
|
289
|
-
try {
|
|
290
|
-
const cachePath = getEntitlementsCachePath(projectPath);
|
|
291
|
-
const dir = path.dirname(cachePath);
|
|
292
|
-
if (!fs.existsSync(dir)) fs.mkdirSync(dir, { recursive: true });
|
|
293
|
-
fs.writeFileSync(cachePath, JSON.stringify({ tier: _cachedTier, fetchedAt: new Date().toISOString() }, null, 2));
|
|
294
|
-
} catch {}
|
|
295
|
-
|
|
296
139
|
return _cachedTier;
|
|
297
140
|
}
|
|
298
|
-
|
|
299
|
-
if (res.status === 401) {
|
|
300
|
-
return "free"; // Invalid key = free tier
|
|
301
|
-
}
|
|
302
141
|
} catch {
|
|
303
|
-
// Network error -
|
|
304
|
-
try {
|
|
305
|
-
const cachePath = getEntitlementsCachePath(projectPath);
|
|
306
|
-
if (fs.existsSync(cachePath)) {
|
|
307
|
-
const cached = JSON.parse(fs.readFileSync(cachePath, "utf8"));
|
|
308
|
-
// Only use cache if less than 24 hours old
|
|
309
|
-
const fetchedAt = new Date(cached.fetchedAt).getTime();
|
|
310
|
-
if (Date.now() - fetchedAt < 24 * 3600 * 1000) {
|
|
311
|
-
return cached.tier || "free";
|
|
312
|
-
}
|
|
313
|
-
}
|
|
314
|
-
} catch {}
|
|
142
|
+
// Network error - default to free
|
|
315
143
|
}
|
|
316
144
|
|
|
317
|
-
// Default to free (no offline bypass to paid features)
|
|
318
145
|
return "free";
|
|
319
146
|
}
|
|
320
147
|
|
|
321
|
-
//
|
|
322
|
-
//
|
|
323
|
-
//
|
|
324
|
-
function getLimits(tier) {
|
|
325
|
-
return LIMITS[tier] || LIMITS.free;
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
329
|
-
// CORE API: enforce() - THE GATEKEEPER
|
|
330
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
331
|
-
/**
|
|
332
|
-
* Enforce feature access. Returns enforcement result.
|
|
333
|
-
*
|
|
334
|
-
* @param {string} feature - Feature key (e.g., "prove", "fix.apply_patches")
|
|
335
|
-
* @param {object} options - { apiKey?, projectPath?, silent? }
|
|
336
|
-
* @returns {object} - { allowed, tier, downgrade?, exitCode, message }
|
|
337
|
-
*/
|
|
148
|
+
// ============================================================================
|
|
149
|
+
// ENFORCE
|
|
150
|
+
// ============================================================================
|
|
338
151
|
async function enforce(feature, options = {}) {
|
|
339
|
-
const { apiKey,
|
|
152
|
+
const { apiKey, silent = false } = options;
|
|
153
|
+
const tier = await getTier({ apiKey });
|
|
340
154
|
|
|
341
|
-
const
|
|
342
|
-
const entitlement = ENTITLEMENTS[feature];
|
|
343
|
-
|
|
344
|
-
if (!entitlement) {
|
|
345
|
-
// Unknown feature - block by default
|
|
346
|
-
return {
|
|
347
|
-
allowed: false,
|
|
348
|
-
tier,
|
|
349
|
-
exitCode: EXIT_MISCONFIG,
|
|
350
|
-
message: `Unknown feature: ${feature}`,
|
|
351
|
-
};
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
const hasAccess = tierMeetsMinimum(tier, entitlement.minTier);
|
|
155
|
+
const hasAccess = tierHasFeature(tier, feature);
|
|
355
156
|
|
|
356
157
|
if (hasAccess) {
|
|
357
|
-
|
|
358
|
-
return {
|
|
359
|
-
allowed: true,
|
|
360
|
-
tier,
|
|
361
|
-
limits: getLimits(tier),
|
|
362
|
-
caps: entitlement.caps?.[tier] || null,
|
|
363
|
-
};
|
|
364
|
-
}
|
|
365
|
-
|
|
366
|
-
// Check for downgrade option
|
|
367
|
-
if (entitlement.downgrade) {
|
|
368
|
-
const downgradeEntitlement = ENTITLEMENTS[entitlement.downgrade];
|
|
369
|
-
if (downgradeEntitlement && tierMeetsMinimum(tier, downgradeEntitlement.minTier)) {
|
|
370
|
-
// Downgrade allowed
|
|
371
|
-
const caps = downgradeEntitlement.caps?.[tier] || null;
|
|
372
|
-
const message = formatDowngradeMessage(feature, entitlement.downgrade, tier, entitlement.minTier, caps);
|
|
373
|
-
|
|
374
|
-
if (!silent) {
|
|
375
|
-
console.log(message);
|
|
376
|
-
}
|
|
377
|
-
|
|
378
|
-
return {
|
|
379
|
-
allowed: true,
|
|
380
|
-
tier,
|
|
381
|
-
downgrade: entitlement.downgrade,
|
|
382
|
-
limits: getLimits(tier),
|
|
383
|
-
caps,
|
|
384
|
-
message,
|
|
385
|
-
};
|
|
386
|
-
}
|
|
158
|
+
return { allowed: true, tier };
|
|
387
159
|
}
|
|
388
160
|
|
|
389
|
-
|
|
390
|
-
const message = formatUpgradeMessage(feature, tier, entitlement.minTier);
|
|
391
|
-
|
|
161
|
+
const message = formatUpgradeMessage(feature);
|
|
392
162
|
if (!silent) {
|
|
393
163
|
console.error(message);
|
|
394
164
|
}
|
|
@@ -396,164 +166,100 @@ async function enforce(feature, options = {}) {
|
|
|
396
166
|
return {
|
|
397
167
|
allowed: false,
|
|
398
168
|
tier,
|
|
399
|
-
requiredTier: entitlement.minTier,
|
|
400
169
|
exitCode: EXIT_FEATURE_NOT_ALLOWED,
|
|
401
170
|
message,
|
|
402
171
|
};
|
|
403
172
|
}
|
|
404
173
|
|
|
405
|
-
|
|
174
|
+
async function enforceOrExit(feature, options = {}) {
|
|
175
|
+
const result = await enforce(feature, options);
|
|
176
|
+
if (!result.allowed) {
|
|
177
|
+
process.exit(result.exitCode);
|
|
178
|
+
}
|
|
179
|
+
return result;
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
async function checkCommand(command, options = {}) {
|
|
183
|
+
return enforce(command, { ...options, silent: true });
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
// ============================================================================
|
|
406
187
|
// MESSAGING
|
|
407
|
-
//
|
|
188
|
+
// ============================================================================
|
|
408
189
|
const c = {
|
|
409
190
|
reset: "\x1b[0m",
|
|
410
191
|
bold: "\x1b[1m",
|
|
411
|
-
dim: "\x1b[2m",
|
|
412
|
-
red: "\x1b[31m",
|
|
413
|
-
green: "\x1b[32m",
|
|
414
|
-
yellow: "\x1b[33m",
|
|
415
192
|
cyan: "\x1b[36m",
|
|
416
|
-
|
|
193
|
+
yellow: "\x1b[33m",
|
|
417
194
|
};
|
|
418
195
|
|
|
419
|
-
function formatUpgradeMessage(feature
|
|
420
|
-
const tierColors = { starter: c.cyan, pro: c.magenta, enterprise: c.yellow };
|
|
421
|
-
const reqColor = tierColors[requiredTier] || c.yellow;
|
|
422
|
-
|
|
196
|
+
function formatUpgradeMessage(feature) {
|
|
423
197
|
return `
|
|
424
|
-
${c.
|
|
425
|
-
|
|
426
|
-
${c.yellow}${feature}${c.reset} requires ${reqColor}${getTierLabel(requiredTier)}${c.reset} plan.
|
|
427
|
-
Your current plan: ${c.dim}${getTierLabel(currentTier)}${c.reset}
|
|
198
|
+
${c.bold}This feature requires Pro.${c.reset}
|
|
428
199
|
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
${c.dim}Exit code: ${EXIT_FEATURE_NOT_ALLOWED}${c.reset}
|
|
432
|
-
`;
|
|
433
|
-
}
|
|
200
|
+
${c.yellow}${feature}${c.reset} is a Pro feature.
|
|
434
201
|
|
|
435
|
-
|
|
436
|
-
const tierColors = { starter: c.cyan, pro: c.magenta, enterprise: c.yellow };
|
|
437
|
-
const reqColor = tierColors[requiredTier] || c.yellow;
|
|
438
|
-
|
|
439
|
-
let capsStr = "";
|
|
440
|
-
if (caps) {
|
|
441
|
-
if (typeof caps === "string") {
|
|
442
|
-
capsStr = ` ${c.dim}Mode: ${caps}${c.reset}\n`;
|
|
443
|
-
} else if (typeof caps === "object") {
|
|
444
|
-
const entries = Object.entries(caps).map(([k, v]) => `${k}: ${v}`).join(", ");
|
|
445
|
-
capsStr = ` ${c.dim}Limits: ${entries}${c.reset}\n`;
|
|
446
|
-
}
|
|
447
|
-
}
|
|
448
|
-
|
|
449
|
-
return `
|
|
450
|
-
${c.yellow}${c.bold}⚠ Running in Preview Mode${c.reset}
|
|
202
|
+
Upgrade to Pro ($69/mo) to unlock Fix, Prove & Enforce capabilities.
|
|
451
203
|
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
${capsStr}
|
|
455
|
-
${c.cyan}Upgrade for full access:${c.reset} https://vibecheckai.dev/pricing
|
|
204
|
+
vibecheck upgrade
|
|
205
|
+
https://vibecheckai.dev/pricing
|
|
456
206
|
`;
|
|
457
207
|
}
|
|
458
208
|
|
|
459
|
-
//
|
|
460
|
-
//
|
|
461
|
-
//
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
const result = await enforce(feature, options);
|
|
475
|
-
if (!result.allowed) {
|
|
476
|
-
process.exit(result.exitCode);
|
|
477
|
-
}
|
|
478
|
-
return result;
|
|
479
|
-
}
|
|
480
|
-
|
|
481
|
-
/**
|
|
482
|
-
* Get the minimum tier required for a feature
|
|
483
|
-
*/
|
|
484
|
-
function getMinTierForFeature(feature) {
|
|
485
|
-
return ENTITLEMENTS[feature]?.minTier || "enterprise";
|
|
486
|
-
}
|
|
209
|
+
// ============================================================================
|
|
210
|
+
// TIER LIMITS
|
|
211
|
+
// ============================================================================
|
|
212
|
+
const TIER_LIMITS = {
|
|
213
|
+
free: {
|
|
214
|
+
reportFormats: ["html", "md", "json"],
|
|
215
|
+
maxScansPerMonth: 100,
|
|
216
|
+
maxFilesPerScan: 1000,
|
|
217
|
+
},
|
|
218
|
+
pro: {
|
|
219
|
+
reportFormats: ["html", "md", "json", "sarif", "csv", "pdf"],
|
|
220
|
+
maxScansPerMonth: -1, // unlimited
|
|
221
|
+
maxFilesPerScan: -1, // unlimited
|
|
222
|
+
},
|
|
223
|
+
};
|
|
487
224
|
|
|
488
225
|
/**
|
|
489
|
-
*
|
|
226
|
+
* Get limits for a tier
|
|
490
227
|
*/
|
|
491
|
-
function
|
|
492
|
-
|
|
493
|
-
if (!entitlement) return false;
|
|
494
|
-
return tierMeetsMinimum(tier, entitlement.minTier);
|
|
228
|
+
function getLimits(tier) {
|
|
229
|
+
return TIER_LIMITS[tier] || TIER_LIMITS.free;
|
|
495
230
|
}
|
|
496
231
|
|
|
497
232
|
/**
|
|
498
|
-
*
|
|
233
|
+
* Check if current tier meets minimum required tier
|
|
499
234
|
*/
|
|
500
|
-
function
|
|
501
|
-
const
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
}
|
|
506
|
-
}
|
|
507
|
-
return features;
|
|
508
|
-
}
|
|
509
|
-
|
|
510
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
511
|
-
// COMMAND GROUPING FOR HELP DISPLAY
|
|
512
|
-
// ═══════════════════════════════════════════════════════════════════════════════
|
|
513
|
-
const COMMAND_GROUPS = {
|
|
514
|
-
"Proof Loop": ["scan", "ship", "reality", "prove", "fix", "report"],
|
|
515
|
-
"Setup & DX": ["install", "init", "doctor", "status", "watch", "launch"],
|
|
516
|
-
"AI Truth": ["ctx", "guard", "context", "mdc"],
|
|
517
|
-
"CI & Collaboration": ["gate", "pr", "badge"],
|
|
518
|
-
"Reporting": ["report"],
|
|
519
|
-
"Automation": ["ai-test", "mcp", "share"],
|
|
520
|
-
};
|
|
521
|
-
|
|
522
|
-
function getCommandGroup(command) {
|
|
523
|
-
for (const [group, commands] of Object.entries(COMMAND_GROUPS)) {
|
|
524
|
-
if (commands.includes(command)) return group;
|
|
525
|
-
}
|
|
526
|
-
return "Other";
|
|
235
|
+
function tierMeetsMinimum(current, required) {
|
|
236
|
+
const tierOrder = ['free', 'pro'];
|
|
237
|
+
const currentIndex = tierOrder.indexOf(current);
|
|
238
|
+
const requiredIndex = tierOrder.indexOf(required);
|
|
239
|
+
return currentIndex >= requiredIndex;
|
|
527
240
|
}
|
|
528
241
|
|
|
529
|
-
//
|
|
242
|
+
// ============================================================================
|
|
530
243
|
// EXPORTS
|
|
531
|
-
//
|
|
244
|
+
// ============================================================================
|
|
532
245
|
module.exports = {
|
|
533
|
-
// Core
|
|
246
|
+
// Core
|
|
534
247
|
getTier,
|
|
535
|
-
getLimits,
|
|
536
248
|
enforce,
|
|
537
249
|
enforceOrExit,
|
|
538
250
|
checkCommand,
|
|
539
251
|
|
|
540
|
-
//
|
|
541
|
-
|
|
542
|
-
getTierLabel,
|
|
543
|
-
getMinTierForFeature,
|
|
252
|
+
// Helpers
|
|
253
|
+
isPro,
|
|
544
254
|
tierHasFeature,
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
// Command grouping
|
|
548
|
-
COMMAND_GROUPS,
|
|
549
|
-
getCommandGroup,
|
|
255
|
+
getLimits,
|
|
256
|
+
tierMeetsMinimum,
|
|
550
257
|
|
|
551
258
|
// Constants
|
|
552
259
|
TIERS,
|
|
553
|
-
|
|
554
|
-
|
|
260
|
+
TIER_LIMITS,
|
|
261
|
+
FREE_FEATURES,
|
|
262
|
+
PRO_FEATURES,
|
|
555
263
|
EXIT_SUCCESS,
|
|
556
|
-
EXIT_BLOCK_VERDICT,
|
|
557
264
|
EXIT_FEATURE_NOT_ALLOWED,
|
|
558
|
-
EXIT_MISCONFIG,
|
|
559
265
|
};
|