vibecheck-ai 2.0.1 → 5.0.0
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/.generated +25 -0
- package/bin/_deprecations.js +463 -0
- package/bin/_router.js +46 -0
- package/bin/cli-hygiene.js +241 -0
- package/bin/dev/run-v2-torture.js +30 -0
- package/bin/registry.js +656 -0
- package/bin/runners/CLI_REFACTOR_SUMMARY.md +229 -0
- package/bin/runners/ENHANCEMENT_GUIDE.md +121 -0
- package/bin/runners/REPORT_AUDIT.md +64 -0
- package/bin/runners/cli-utils.js +1070 -0
- package/bin/runners/context/ai-task-decomposer.js +337 -0
- package/bin/runners/context/analyzer.js +513 -0
- package/bin/runners/context/api-contracts.js +427 -0
- package/bin/runners/context/context-diff.js +342 -0
- package/bin/runners/context/context-pruner.js +291 -0
- package/bin/runners/context/dependency-graph.js +414 -0
- package/bin/runners/context/generators/claude.js +107 -0
- package/bin/runners/context/generators/codex.js +108 -0
- package/bin/runners/context/generators/copilot.js +119 -0
- package/bin/runners/context/generators/cursor-enhanced.js +2525 -0
- package/bin/runners/context/generators/cursor.js +514 -0
- package/bin/runners/context/generators/mcp.js +169 -0
- package/bin/runners/context/generators/windsurf.js +180 -0
- package/bin/runners/context/git-context.js +304 -0
- package/bin/runners/context/index.js +1110 -0
- package/bin/runners/context/insights.js +173 -0
- package/bin/runners/context/mcp-server/generate-rules.js +337 -0
- package/bin/runners/context/mcp-server/index.js +1176 -0
- package/bin/runners/context/mcp-server/package.json +24 -0
- package/bin/runners/context/memory.js +200 -0
- package/bin/runners/context/monorepo.js +215 -0
- package/bin/runners/context/multi-repo-federation.js +404 -0
- package/bin/runners/context/patterns.js +253 -0
- package/bin/runners/context/proof-context.js +1264 -0
- package/bin/runners/context/security-scanner.js +541 -0
- package/bin/runners/context/semantic-search.js +350 -0
- package/bin/runners/context/shared.js +264 -0
- package/bin/runners/context/team-conventions.js +336 -0
- package/bin/runners/lib/__tests__/entitlements-v2.test.js +295 -0
- 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/enforcement/gateway.js +1059 -0
- package/bin/runners/lib/agent-firewall/enforcement/index.js +98 -0
- package/bin/runners/lib/agent-firewall/enforcement/mode.js +318 -0
- package/bin/runners/lib/agent-firewall/enforcement/orchestrator.js +484 -0
- package/bin/runners/lib/agent-firewall/enforcement/proof-artifact.js +418 -0
- package/bin/runners/lib/agent-firewall/enforcement/schemas/change-event.schema.json +173 -0
- package/bin/runners/lib/agent-firewall/enforcement/schemas/intent.schema.json +181 -0
- package/bin/runners/lib/agent-firewall/enforcement/schemas/verdict.schema.json +222 -0
- package/bin/runners/lib/agent-firewall/enforcement/verdict-v2.js +333 -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/index.js +200 -0
- package/bin/runners/lib/agent-firewall/integration/index.js +20 -0
- package/bin/runners/lib/agent-firewall/integration/ship-gate.js +437 -0
- package/bin/runners/lib/agent-firewall/intent/alignment-engine.js +634 -0
- package/bin/runners/lib/agent-firewall/intent/auto-detect.js +426 -0
- package/bin/runners/lib/agent-firewall/intent/index.js +102 -0
- package/bin/runners/lib/agent-firewall/intent/schema.js +352 -0
- package/bin/runners/lib/agent-firewall/intent/store.js +283 -0
- package/bin/runners/lib/agent-firewall/interception/fs-interceptor.js +502 -0
- package/bin/runners/lib/agent-firewall/interception/index.js +23 -0
- package/bin/runners/lib/agent-firewall/interceptor/base.js +308 -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 +79 -0
- package/bin/runners/lib/agent-firewall/policy/rules/ghost-env.js +227 -0
- package/bin/runners/lib/agent-firewall/policy/rules/ghost-route.js +191 -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 +322 -0
- package/bin/runners/lib/agent-firewall/risk/vectors.js +421 -0
- package/bin/runners/lib/agent-firewall/session/collector.js +451 -0
- package/bin/runners/lib/agent-firewall/session/index.js +26 -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/ai-bridge.js +416 -0
- package/bin/runners/lib/analysis-core.js +309 -0
- package/bin/runners/lib/analyzers.js +2500 -0
- package/bin/runners/lib/api-client.js +269 -0
- package/bin/runners/lib/approve-output.js +235 -0
- package/bin/runners/lib/artifact-envelope.js +540 -0
- package/bin/runners/lib/assets/vibecheck-logo.png +0 -0
- package/bin/runners/lib/audit-bridge.js +391 -0
- package/bin/runners/lib/auth-shared.js +977 -0
- package/bin/runners/lib/auth-truth.js +193 -0
- package/bin/runners/lib/auth.js +215 -0
- package/bin/runners/lib/authority-badge.js +425 -0
- package/bin/runners/lib/backup.js +62 -0
- package/bin/runners/lib/billing.js +107 -0
- package/bin/runners/lib/checkpoint.js +941 -0
- package/bin/runners/lib/claims.js +118 -0
- package/bin/runners/lib/classify-output.js +204 -0
- package/bin/runners/lib/cleanup/engine.js +571 -0
- package/bin/runners/lib/cleanup/index.js +53 -0
- package/bin/runners/lib/cleanup/output.js +375 -0
- package/bin/runners/lib/cleanup/rules.js +1060 -0
- package/bin/runners/lib/cli-output.js +400 -0
- package/bin/runners/lib/cli-ui.js +540 -0
- package/bin/runners/lib/compliance-bridge-new.js +0 -0
- package/bin/runners/lib/compliance-bridge.js +165 -0
- package/bin/runners/lib/contracts/auth-contract.js +202 -0
- package/bin/runners/lib/contracts/env-contract.js +181 -0
- package/bin/runners/lib/contracts/external-contract.js +206 -0
- package/bin/runners/lib/contracts/guard.js +168 -0
- package/bin/runners/lib/contracts/index.js +89 -0
- package/bin/runners/lib/contracts/plan-validator.js +311 -0
- package/bin/runners/lib/contracts/route-contract.js +199 -0
- package/bin/runners/lib/contracts.js +804 -0
- package/bin/runners/lib/default-config.js +127 -0
- package/bin/runners/lib/detect.js +89 -0
- package/bin/runners/lib/detectors-v2.js +622 -0
- package/bin/runners/lib/doctor/autofix.js +254 -0
- package/bin/runners/lib/doctor/diagnosis-receipt.js +454 -0
- package/bin/runners/lib/doctor/failure-signatures.js +526 -0
- package/bin/runners/lib/doctor/fix-script.js +336 -0
- package/bin/runners/lib/doctor/index.js +37 -0
- package/bin/runners/lib/doctor/modules/build-tools.js +453 -0
- package/bin/runners/lib/doctor/modules/dependencies.js +325 -0
- package/bin/runners/lib/doctor/modules/index.js +105 -0
- package/bin/runners/lib/doctor/modules/network.js +250 -0
- package/bin/runners/lib/doctor/modules/os-quirks.js +706 -0
- package/bin/runners/lib/doctor/modules/project.js +312 -0
- package/bin/runners/lib/doctor/modules/repo-integrity.js +485 -0
- package/bin/runners/lib/doctor/modules/runtime.js +224 -0
- package/bin/runners/lib/doctor/modules/security.js +350 -0
- package/bin/runners/lib/doctor/modules/system.js +213 -0
- package/bin/runners/lib/doctor/modules/vibecheck.js +394 -0
- package/bin/runners/lib/doctor/reporter.js +262 -0
- package/bin/runners/lib/doctor/safe-repair.js +384 -0
- package/bin/runners/lib/doctor/service.js +262 -0
- package/bin/runners/lib/doctor/types.js +113 -0
- package/bin/runners/lib/doctor/ui.js +263 -0
- package/bin/runners/lib/doctor-enhanced.js +233 -0
- package/bin/runners/lib/doctor-output.js +226 -0
- package/bin/runners/lib/doctor-v2.js +608 -0
- package/bin/runners/lib/drift.js +425 -0
- package/bin/runners/lib/enforcement.js +72 -0
- 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/attack-detector.js +1192 -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/enterprise-detect.js +603 -0
- package/bin/runners/lib/enterprise-init.js +942 -0
- package/bin/runners/lib/entitlements-v2.js +265 -0
- package/bin/runners/lib/entitlements.generated.js +0 -0
- package/bin/runners/lib/entitlements.js +340 -0
- package/bin/runners/lib/env-resolver.js +417 -0
- package/bin/runners/lib/env-template.js +66 -0
- package/bin/runners/lib/env.js +189 -0
- package/bin/runners/lib/error-handler.js +368 -0
- package/bin/runners/lib/error-messages.js +289 -0
- package/bin/runners/lib/evidence-pack.js +684 -0
- package/bin/runners/lib/exit-codes.js +275 -0
- package/bin/runners/lib/extractors/client-calls.js +990 -0
- package/bin/runners/lib/extractors/fastify-route-dump.js +573 -0
- package/bin/runners/lib/extractors/fastify-routes.js +426 -0
- package/bin/runners/lib/extractors/index.js +363 -0
- package/bin/runners/lib/extractors/next-routes.js +524 -0
- package/bin/runners/lib/extractors/proof-graph.js +431 -0
- package/bin/runners/lib/extractors/route-matcher.js +451 -0
- package/bin/runners/lib/extractors/truthpack-v2.js +377 -0
- package/bin/runners/lib/extractors/ui-bindings.js +547 -0
- package/bin/runners/lib/finding-id.js +69 -0
- package/bin/runners/lib/finding-sorter.js +89 -0
- package/bin/runners/lib/findings-schema.js +281 -0
- package/bin/runners/lib/fingerprint.js +377 -0
- package/bin/runners/lib/firewall-prompt.js +50 -0
- package/bin/runners/lib/fix-output.js +228 -0
- package/bin/runners/lib/global-flags.js +250 -0
- package/bin/runners/lib/graph/graph-builder.js +265 -0
- package/bin/runners/lib/graph/html-renderer.js +413 -0
- package/bin/runners/lib/graph/index.js +32 -0
- package/bin/runners/lib/graph/runtime-collector.js +215 -0
- package/bin/runners/lib/graph/static-extractor.js +518 -0
- package/bin/runners/lib/help-formatter.js +413 -0
- package/bin/runners/lib/html-proof-report.js +913 -0
- package/bin/runners/lib/html-report.js +650 -0
- package/bin/runners/lib/init-wizard.js +601 -0
- package/bin/runners/lib/interactive-menu.js +1496 -0
- package/bin/runners/lib/json-output.js +76 -0
- package/bin/runners/lib/llm.js +75 -0
- package/bin/runners/lib/logger.js +38 -0
- package/bin/runners/lib/meter.js +61 -0
- package/bin/runners/lib/missions/briefing.js +427 -0
- package/bin/runners/lib/missions/checkpoint.js +753 -0
- package/bin/runners/lib/missions/evidence.js +126 -0
- package/bin/runners/lib/missions/hardening.js +851 -0
- package/bin/runners/lib/missions/plan.js +648 -0
- package/bin/runners/lib/missions/safety-gates.js +645 -0
- package/bin/runners/lib/missions/schema.js +478 -0
- package/bin/runners/lib/missions/templates.js +317 -0
- package/bin/runners/lib/next-action.js +560 -0
- package/bin/runners/lib/packs/bundle.js +675 -0
- package/bin/runners/lib/packs/evidence-pack.js +671 -0
- package/bin/runners/lib/packs/pack-factory.js +837 -0
- package/bin/runners/lib/packs/permissions-pack.js +686 -0
- package/bin/runners/lib/packs/proof-graph-pack.js +779 -0
- package/bin/runners/lib/patch.js +40 -0
- package/bin/runners/lib/permissions/auth-model.js +213 -0
- package/bin/runners/lib/permissions/idor-prover.js +205 -0
- package/bin/runners/lib/permissions/index.js +45 -0
- package/bin/runners/lib/permissions/matrix-builder.js +198 -0
- package/bin/runners/lib/pkgjson.js +28 -0
- package/bin/runners/lib/policy.js +295 -0
- package/bin/runners/lib/polish/accessibility.js +62 -0
- package/bin/runners/lib/polish/analyzer.js +93 -0
- package/bin/runners/lib/polish/backend.js +87 -0
- package/bin/runners/lib/polish/configuration.js +83 -0
- package/bin/runners/lib/polish/documentation.js +83 -0
- package/bin/runners/lib/polish/frontend.js +817 -0
- package/bin/runners/lib/polish/index.js +27 -0
- package/bin/runners/lib/polish/infrastructure.js +80 -0
- package/bin/runners/lib/polish/internationalization.js +85 -0
- package/bin/runners/lib/polish/libraries.js +180 -0
- package/bin/runners/lib/polish/observability.js +75 -0
- package/bin/runners/lib/polish/performance.js +64 -0
- package/bin/runners/lib/polish/privacy.js +110 -0
- package/bin/runners/lib/polish/resilience.js +92 -0
- package/bin/runners/lib/polish/security.js +78 -0
- package/bin/runners/lib/polish/seo.js +71 -0
- package/bin/runners/lib/polish/styles.js +62 -0
- package/bin/runners/lib/polish/utils.js +104 -0
- package/bin/runners/lib/preflight.js +142 -0
- package/bin/runners/lib/prerequisites.js +149 -0
- package/bin/runners/lib/prove-output.js +220 -0
- package/bin/runners/lib/reality/correlation-detectors.js +359 -0
- package/bin/runners/lib/reality/index.js +318 -0
- package/bin/runners/lib/reality/request-hashing.js +416 -0
- package/bin/runners/lib/reality/request-mapper.js +453 -0
- package/bin/runners/lib/reality/safety-rails.js +463 -0
- package/bin/runners/lib/reality/semantic-snapshot.js +408 -0
- package/bin/runners/lib/reality/toast-detector.js +393 -0
- package/bin/runners/lib/reality-findings.js +84 -0
- package/bin/runners/lib/reality-output.js +231 -0
- package/bin/runners/lib/receipts.js +179 -0
- package/bin/runners/lib/redact.js +29 -0
- package/bin/runners/lib/replay/capsule-manager.js +154 -0
- package/bin/runners/lib/replay/index.js +263 -0
- package/bin/runners/lib/replay/player.js +348 -0
- package/bin/runners/lib/replay/recorder.js +331 -0
- package/bin/runners/lib/report-engine.js +626 -0
- package/bin/runners/lib/report-html.js +1233 -0
- package/bin/runners/lib/report-output.js +366 -0
- package/bin/runners/lib/report-templates.js +967 -0
- package/bin/runners/lib/report.js +135 -0
- package/bin/runners/lib/route-detection.js +1209 -0
- package/bin/runners/lib/route-truth.js +1322 -0
- package/bin/runners/lib/safelist/index.js +96 -0
- package/bin/runners/lib/safelist/integration.js +334 -0
- package/bin/runners/lib/safelist/matcher.js +696 -0
- package/bin/runners/lib/safelist/schema.js +948 -0
- package/bin/runners/lib/safelist/store.js +438 -0
- package/bin/runners/lib/sandbox/index.js +59 -0
- package/bin/runners/lib/sandbox/proof-chain.js +399 -0
- package/bin/runners/lib/sandbox/sandbox-runner.js +205 -0
- package/bin/runners/lib/sandbox/worktree.js +174 -0
- package/bin/runners/lib/scan-cache.js +330 -0
- package/bin/runners/lib/scan-output-schema.js +344 -0
- package/bin/runners/lib/scan-output.js +631 -0
- package/bin/runners/lib/scan-runner.js +135 -0
- package/bin/runners/lib/schema-validator.js +350 -0
- package/bin/runners/lib/schemas/ajv-validator.js +464 -0
- package/bin/runners/lib/schemas/contracts.schema.json +160 -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/finding.schema.json +100 -0
- package/bin/runners/lib/schemas/mission-pack.schema.json +206 -0
- package/bin/runners/lib/schemas/proof-graph.schema.json +176 -0
- package/bin/runners/lib/schemas/reality-report.schema.json +162 -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/share-pack.schema.json +180 -0
- package/bin/runners/lib/schemas/ship-manifest.schema.json +251 -0
- package/bin/runners/lib/schemas/ship-report.schema.json +117 -0
- package/bin/runners/lib/schemas/truthpack-v2.schema.json +303 -0
- package/bin/runners/lib/schemas/validator.js +465 -0
- package/bin/runners/lib/schemas/verdict.schema.json +140 -0
- package/bin/runners/lib/score-history.js +282 -0
- package/bin/runners/lib/security-bridge.js +249 -0
- package/bin/runners/lib/server-usage.js +513 -0
- package/bin/runners/lib/share-pack.js +239 -0
- package/bin/runners/lib/ship-gate.js +832 -0
- package/bin/runners/lib/ship-manifest.js +1153 -0
- package/bin/runners/lib/ship-output-enterprise.js +239 -0
- package/bin/runners/lib/ship-output.js +1128 -0
- package/bin/runners/lib/snippets.js +67 -0
- package/bin/runners/lib/status-output.js +340 -0
- package/bin/runners/lib/terminal-ui.js +356 -0
- package/bin/runners/lib/truth.js +1691 -0
- package/bin/runners/lib/ui.js +562 -0
- package/bin/runners/lib/unified-cli-output.js +947 -0
- package/bin/runners/lib/unified-output.js +197 -0
- package/bin/runners/lib/upsell.js +410 -0
- package/bin/runners/lib/usage.js +153 -0
- package/bin/runners/lib/validate-patch.js +156 -0
- package/bin/runners/lib/verdict-engine.js +628 -0
- package/bin/runners/lib/verification.js +345 -0
- package/bin/runners/lib/why-tree.js +650 -0
- package/bin/runners/reality/engine.js +917 -0
- package/bin/runners/reality/flows.js +122 -0
- package/bin/runners/reality/report.js +378 -0
- package/bin/runners/reality/session.js +193 -0
- package/bin/runners/runAIAgent.js +229 -0
- package/bin/runners/runAgent.d.ts +5 -0
- package/bin/runners/runAgent.js +161 -0
- package/bin/runners/runAllowlist.js +418 -0
- package/bin/runners/runApprove.js +320 -0
- package/bin/runners/runAudit.js +692 -0
- package/bin/runners/runAuth.js +731 -0
- package/bin/runners/runCI.js +353 -0
- package/bin/runners/runCheckpoint.js +530 -0
- package/bin/runners/runClassify.js +928 -0
- package/bin/runners/runCleanup.js +343 -0
- package/bin/runners/runContext.d.ts +4 -0
- package/bin/runners/runContext.js +175 -0
- package/bin/runners/runDoctor.js +877 -0
- package/bin/runners/runEvidencePack.js +362 -0
- 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 +1355 -0
- package/bin/runners/runForge.js +451 -0
- package/bin/runners/runGuard.js +262 -0
- package/bin/runners/runInit.js +1927 -0
- package/bin/runners/runIntent.js +906 -0
- package/bin/runners/runKickoff.js +878 -0
- package/bin/runners/runLabs.js +424 -0
- package/bin/runners/runLaunch.js +2000 -0
- package/bin/runners/runLink.js +785 -0
- package/bin/runners/runMcp.js +1875 -0
- package/bin/runners/runPacks.js +2089 -0
- package/bin/runners/runPolish.d.ts +4 -0
- package/bin/runners/runPolish.js +390 -0
- package/bin/runners/runPromptFirewall.js +211 -0
- package/bin/runners/runProve.js +1411 -0
- package/bin/runners/runQuickstart.js +531 -0
- package/bin/runners/runReality.js +2260 -0
- package/bin/runners/runReport.js +726 -0
- package/bin/runners/runRuntime.js +110 -0
- package/bin/runners/runSafelist.js +1190 -0
- package/bin/runners/runScan.js +688 -0
- package/bin/runners/runShield.js +1282 -0
- package/bin/runners/runShip.js +1660 -0
- package/bin/runners/runTruth.d.ts +5 -0
- package/bin/runners/runTruth.js +101 -0
- package/bin/runners/runValidate.js +179 -0
- package/bin/runners/runWatch.js +478 -0
- package/bin/runners/utils.js +360 -0
- package/bin/scan.js +617 -0
- package/bin/vibecheck.js +1617 -0
- package/dist/guardrail/index.d.ts +2405 -0
- package/dist/guardrail/index.js +9747 -0
- package/dist/guardrail/index.js.map +1 -0
- package/dist/scanner/index.d.ts +282 -0
- package/dist/scanner/index.js +3395 -0
- package/dist/scanner/index.js.map +1 -0
- package/package.json +123 -104
- package/README.md +0 -491
- package/dist/index.js +0 -99711
- package/dist/index.js.map +0 -1
|
@@ -0,0 +1,386 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Proposal Validator
|
|
3
|
+
*
|
|
4
|
+
* Validates change proposals against the schema and semantic rules.
|
|
5
|
+
* Rejects incomplete, vague, or unsafe proposals.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
"use strict";
|
|
9
|
+
|
|
10
|
+
const { PROPOSAL_SCHEMA, DEFAULT_PROPOSAL_VALUES, normalizeIntent } = require("./schema");
|
|
11
|
+
const { classifyFileDomain } = require("../reality/state");
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* @typedef {Object} ValidationResult
|
|
15
|
+
* @property {boolean} valid - Whether proposal is valid
|
|
16
|
+
* @property {Array} errors - Validation errors
|
|
17
|
+
* @property {Array} warnings - Validation warnings
|
|
18
|
+
* @property {Object} normalized - Normalized proposal
|
|
19
|
+
*/
|
|
20
|
+
|
|
21
|
+
/**
|
|
22
|
+
* Validate proposal structure
|
|
23
|
+
* @param {Object} proposal - Raw proposal
|
|
24
|
+
* @returns {ValidationResult} Validation result
|
|
25
|
+
*/
|
|
26
|
+
function validateStructure(proposal) {
|
|
27
|
+
const errors = [];
|
|
28
|
+
const warnings = [];
|
|
29
|
+
|
|
30
|
+
// Check required fields
|
|
31
|
+
if (!proposal) {
|
|
32
|
+
errors.push({ field: "proposal", message: "Proposal is required" });
|
|
33
|
+
return { valid: false, errors, warnings };
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
if (!proposal.intent) {
|
|
37
|
+
errors.push({ field: "intent", message: "Intent is required" });
|
|
38
|
+
} else if (typeof proposal.intent !== "string") {
|
|
39
|
+
errors.push({ field: "intent", message: "Intent must be a string" });
|
|
40
|
+
} else if (proposal.intent.length < 3) {
|
|
41
|
+
errors.push({ field: "intent", message: "Intent must be at least 3 characters" });
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
if (!proposal.operations) {
|
|
45
|
+
errors.push({ field: "operations", message: "Operations array is required" });
|
|
46
|
+
} else if (!Array.isArray(proposal.operations)) {
|
|
47
|
+
errors.push({ field: "operations", message: "Operations must be an array" });
|
|
48
|
+
} else if (proposal.operations.length === 0) {
|
|
49
|
+
errors.push({ field: "operations", message: "At least one operation is required" });
|
|
50
|
+
} else {
|
|
51
|
+
// Validate each operation
|
|
52
|
+
for (let i = 0; i < proposal.operations.length; i++) {
|
|
53
|
+
const op = proposal.operations[i];
|
|
54
|
+
|
|
55
|
+
if (!op.type) {
|
|
56
|
+
errors.push({ field: `operations[${i}].type`, message: "Operation type is required" });
|
|
57
|
+
} else if (!["create", "modify", "delete", "rename"].includes(op.type)) {
|
|
58
|
+
errors.push({
|
|
59
|
+
field: `operations[${i}].type`,
|
|
60
|
+
message: `Invalid operation type: ${op.type}. Must be create, modify, delete, or rename`
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
if (!op.path) {
|
|
65
|
+
errors.push({ field: `operations[${i}].path`, message: "Operation path is required" });
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
// Content required for create/modify
|
|
69
|
+
if ((op.type === "create" || op.type === "modify") && !op.content && op.content !== "") {
|
|
70
|
+
warnings.push({
|
|
71
|
+
field: `operations[${i}].content`,
|
|
72
|
+
message: "Content is recommended for create/modify operations"
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
// newPath required for rename
|
|
77
|
+
if (op.type === "rename" && !op.newPath) {
|
|
78
|
+
errors.push({ field: `operations[${i}].newPath`, message: "newPath is required for rename operations" });
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
// Validate optional fields
|
|
84
|
+
if (proposal.confidence !== undefined) {
|
|
85
|
+
if (typeof proposal.confidence !== "number") {
|
|
86
|
+
errors.push({ field: "confidence", message: "Confidence must be a number" });
|
|
87
|
+
} else if (proposal.confidence < 0 || proposal.confidence > 1) {
|
|
88
|
+
errors.push({ field: "confidence", message: "Confidence must be between 0 and 1" });
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
if (proposal.assumptions && !Array.isArray(proposal.assumptions)) {
|
|
93
|
+
errors.push({ field: "assumptions", message: "Assumptions must be an array" });
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
if (proposal.filesTouched && !Array.isArray(proposal.filesTouched)) {
|
|
97
|
+
errors.push({ field: "filesTouched", message: "filesTouched must be an array" });
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
return {
|
|
101
|
+
valid: errors.length === 0,
|
|
102
|
+
errors,
|
|
103
|
+
warnings,
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
/**
|
|
108
|
+
* Validate proposal semantics
|
|
109
|
+
* @param {Object} proposal - Proposal to validate
|
|
110
|
+
* @returns {ValidationResult} Validation result
|
|
111
|
+
*/
|
|
112
|
+
function validateSemantics(proposal) {
|
|
113
|
+
const errors = [];
|
|
114
|
+
const warnings = [];
|
|
115
|
+
|
|
116
|
+
// Check for vague intent
|
|
117
|
+
const vagueIntents = ["fix", "update", "change", "modify", "improve", "refactor"];
|
|
118
|
+
const intentWords = proposal.intent.toLowerCase().split("_");
|
|
119
|
+
if (intentWords.length === 1 && vagueIntents.includes(intentWords[0])) {
|
|
120
|
+
warnings.push({
|
|
121
|
+
field: "intent",
|
|
122
|
+
message: `Intent '${proposal.intent}' is too vague. Be more specific about what is being changed.`,
|
|
123
|
+
});
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
// Check for missing summary on complex changes
|
|
127
|
+
if (proposal.operations.length > 2 && !proposal.summary) {
|
|
128
|
+
warnings.push({
|
|
129
|
+
field: "summary",
|
|
130
|
+
message: "Summary is recommended for changes touching multiple files",
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
// Check for missing assumptions when touching sensitive domains
|
|
135
|
+
const sensitiveDomains = ["auth", "payments", "database", "security"];
|
|
136
|
+
const touchedDomains = new Set();
|
|
137
|
+
|
|
138
|
+
for (const op of proposal.operations) {
|
|
139
|
+
const domain = classifyFileDomain(op.path);
|
|
140
|
+
touchedDomains.add(domain);
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
const sensitiveDomainsAffected = [...touchedDomains].filter(d => sensitiveDomains.includes(d));
|
|
144
|
+
|
|
145
|
+
if (sensitiveDomainsAffected.length > 0 && (!proposal.assumptions || proposal.assumptions.length === 0)) {
|
|
146
|
+
warnings.push({
|
|
147
|
+
field: "assumptions",
|
|
148
|
+
message: `Change affects sensitive domains (${sensitiveDomainsAffected.join(", ")}). Assumptions should be declared.`,
|
|
149
|
+
});
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
// Check for low confidence without explanation
|
|
153
|
+
if (proposal.confidence !== undefined && proposal.confidence < 0.5 && !proposal.summary) {
|
|
154
|
+
warnings.push({
|
|
155
|
+
field: "confidence",
|
|
156
|
+
message: "Low confidence proposals should include a summary explaining uncertainties",
|
|
157
|
+
});
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
// Check filesTouched matches operations
|
|
161
|
+
if (proposal.filesTouched && proposal.operations) {
|
|
162
|
+
const operationPaths = new Set(proposal.operations.map(op => op.path));
|
|
163
|
+
const declaredPaths = new Set(proposal.filesTouched);
|
|
164
|
+
|
|
165
|
+
for (const path of operationPaths) {
|
|
166
|
+
if (!declaredPaths.has(path)) {
|
|
167
|
+
warnings.push({
|
|
168
|
+
field: "filesTouched",
|
|
169
|
+
message: `Operation path '${path}' not listed in filesTouched`,
|
|
170
|
+
});
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
// Check assumptions have required fields
|
|
176
|
+
if (proposal.assumptions) {
|
|
177
|
+
for (let i = 0; i < proposal.assumptions.length; i++) {
|
|
178
|
+
const assumption = proposal.assumptions[i];
|
|
179
|
+
|
|
180
|
+
if (!assumption.type) {
|
|
181
|
+
errors.push({
|
|
182
|
+
field: `assumptions[${i}].type`,
|
|
183
|
+
message: "Assumption type is required",
|
|
184
|
+
});
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
if (!assumption.key && !assumption.path && !assumption.value) {
|
|
188
|
+
errors.push({
|
|
189
|
+
field: `assumptions[${i}]`,
|
|
190
|
+
message: "Assumption must have key, path, or value",
|
|
191
|
+
});
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
if (!assumption.reason) {
|
|
195
|
+
warnings.push({
|
|
196
|
+
field: `assumptions[${i}].reason`,
|
|
197
|
+
message: "Assumption should explain why it's needed",
|
|
198
|
+
});
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
return {
|
|
204
|
+
valid: errors.length === 0,
|
|
205
|
+
errors,
|
|
206
|
+
warnings,
|
|
207
|
+
};
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
/**
|
|
211
|
+
* Validate proposal completeness
|
|
212
|
+
* @param {Object} proposal - Proposal to validate
|
|
213
|
+
* @param {Object} options - Validation options
|
|
214
|
+
* @returns {ValidationResult} Validation result
|
|
215
|
+
*/
|
|
216
|
+
function validateCompleteness(proposal, options = {}) {
|
|
217
|
+
const { strict = false } = options;
|
|
218
|
+
const errors = [];
|
|
219
|
+
const warnings = [];
|
|
220
|
+
|
|
221
|
+
// In strict mode, require more fields
|
|
222
|
+
if (strict) {
|
|
223
|
+
if (!proposal.summary) {
|
|
224
|
+
errors.push({ field: "summary", message: "Summary is required in strict mode" });
|
|
225
|
+
}
|
|
226
|
+
|
|
227
|
+
if (!proposal.assumptions || proposal.assumptions.length === 0) {
|
|
228
|
+
errors.push({ field: "assumptions", message: "At least one assumption is required in strict mode" });
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
if (proposal.confidence === undefined) {
|
|
232
|
+
errors.push({ field: "confidence", message: "Confidence is required in strict mode" });
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
if (!proposal.riskAcknowledgment) {
|
|
236
|
+
errors.push({ field: "riskAcknowledgment", message: "Risk acknowledgment is required in strict mode" });
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
// Check for empty content in operations
|
|
241
|
+
for (let i = 0; i < proposal.operations.length; i++) {
|
|
242
|
+
const op = proposal.operations[i];
|
|
243
|
+
if (op.type === "create" && (!op.content || op.content.trim() === "")) {
|
|
244
|
+
warnings.push({
|
|
245
|
+
field: `operations[${i}].content`,
|
|
246
|
+
message: "Creating empty file - is this intentional?",
|
|
247
|
+
});
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
// Check for reasonable number of operations
|
|
252
|
+
if (proposal.operations.length > 20) {
|
|
253
|
+
warnings.push({
|
|
254
|
+
field: "operations",
|
|
255
|
+
message: `Large number of operations (${proposal.operations.length}). Consider breaking into smaller proposals.`,
|
|
256
|
+
});
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
return {
|
|
260
|
+
valid: errors.length === 0,
|
|
261
|
+
errors,
|
|
262
|
+
warnings,
|
|
263
|
+
};
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
/**
|
|
267
|
+
* Normalize proposal (fill defaults, clean data)
|
|
268
|
+
* @param {Object} proposal - Raw proposal
|
|
269
|
+
* @returns {Object} Normalized proposal
|
|
270
|
+
*/
|
|
271
|
+
function normalizeProposal(proposal) {
|
|
272
|
+
const normalized = {
|
|
273
|
+
...DEFAULT_PROPOSAL_VALUES,
|
|
274
|
+
...proposal,
|
|
275
|
+
intent: normalizeIntent(proposal.intent || "unknown"),
|
|
276
|
+
filesTouched: proposal.filesTouched || proposal.operations?.map(op => op.path) || [],
|
|
277
|
+
metadata: {
|
|
278
|
+
...DEFAULT_PROPOSAL_VALUES.metadata,
|
|
279
|
+
...proposal.metadata,
|
|
280
|
+
timestamp: proposal.metadata?.timestamp || new Date().toISOString(),
|
|
281
|
+
},
|
|
282
|
+
};
|
|
283
|
+
|
|
284
|
+
// Normalize operations
|
|
285
|
+
normalized.operations = (proposal.operations || []).map(op => ({
|
|
286
|
+
...op,
|
|
287
|
+
path: op.path?.replace(/\\/g, "/"),
|
|
288
|
+
newPath: op.newPath?.replace(/\\/g, "/"),
|
|
289
|
+
}));
|
|
290
|
+
|
|
291
|
+
// Auto-detect risk acknowledgment from file paths
|
|
292
|
+
for (const op of normalized.operations) {
|
|
293
|
+
const domain = classifyFileDomain(op.path);
|
|
294
|
+
if (domain === "auth") normalized.riskAcknowledgment.touchesAuth = true;
|
|
295
|
+
if (domain === "payments") normalized.riskAcknowledgment.touchesPayments = true;
|
|
296
|
+
if (domain === "database") normalized.riskAcknowledgment.touchesDatabase = true;
|
|
297
|
+
if (domain === "core") normalized.riskAcknowledgment.touchesCore = true;
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
// Check for side effects
|
|
301
|
+
const hasSideEffects = normalized.operations.some(op => {
|
|
302
|
+
if (!op.content) return false;
|
|
303
|
+
return (
|
|
304
|
+
op.content.includes("fetch(") ||
|
|
305
|
+
op.content.includes("axios") ||
|
|
306
|
+
op.content.includes("fs.write") ||
|
|
307
|
+
op.content.includes("prisma.") ||
|
|
308
|
+
op.content.includes("exec(")
|
|
309
|
+
);
|
|
310
|
+
});
|
|
311
|
+
normalized.riskAcknowledgment.hasSideEffects = hasSideEffects;
|
|
312
|
+
|
|
313
|
+
// Check for irreversibility
|
|
314
|
+
const isIrreversible = normalized.operations.some(op =>
|
|
315
|
+
op.type === "delete" || op.path.includes("migration")
|
|
316
|
+
);
|
|
317
|
+
normalized.riskAcknowledgment.isIrreversible = isIrreversible;
|
|
318
|
+
|
|
319
|
+
return normalized;
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
/**
|
|
323
|
+
* Full proposal validation
|
|
324
|
+
* @param {Object} proposal - Proposal to validate
|
|
325
|
+
* @param {Object} options - Validation options
|
|
326
|
+
* @returns {ValidationResult} Full validation result
|
|
327
|
+
*/
|
|
328
|
+
function validate(proposal, options = {}) {
|
|
329
|
+
// Structural validation
|
|
330
|
+
const structureResult = validateStructure(proposal);
|
|
331
|
+
if (!structureResult.valid) {
|
|
332
|
+
return {
|
|
333
|
+
valid: false,
|
|
334
|
+
errors: structureResult.errors,
|
|
335
|
+
warnings: structureResult.warnings,
|
|
336
|
+
normalized: null,
|
|
337
|
+
};
|
|
338
|
+
}
|
|
339
|
+
|
|
340
|
+
// Normalize
|
|
341
|
+
const normalized = normalizeProposal(proposal);
|
|
342
|
+
|
|
343
|
+
// Semantic validation
|
|
344
|
+
const semanticResult = validateSemantics(normalized);
|
|
345
|
+
|
|
346
|
+
// Completeness validation
|
|
347
|
+
const completenessResult = validateCompleteness(normalized, options);
|
|
348
|
+
|
|
349
|
+
// Combine results
|
|
350
|
+
const allErrors = [
|
|
351
|
+
...structureResult.errors,
|
|
352
|
+
...semanticResult.errors,
|
|
353
|
+
...completenessResult.errors,
|
|
354
|
+
];
|
|
355
|
+
|
|
356
|
+
const allWarnings = [
|
|
357
|
+
...structureResult.warnings,
|
|
358
|
+
...semanticResult.warnings,
|
|
359
|
+
...completenessResult.warnings,
|
|
360
|
+
];
|
|
361
|
+
|
|
362
|
+
return {
|
|
363
|
+
valid: allErrors.length === 0,
|
|
364
|
+
errors: allErrors,
|
|
365
|
+
warnings: allWarnings,
|
|
366
|
+
normalized,
|
|
367
|
+
};
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
/**
|
|
371
|
+
* Quick validation (structure only)
|
|
372
|
+
* @param {Object} proposal - Proposal to validate
|
|
373
|
+
* @returns {boolean} Is valid
|
|
374
|
+
*/
|
|
375
|
+
function isValid(proposal) {
|
|
376
|
+
return validateStructure(proposal).valid;
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
module.exports = {
|
|
380
|
+
validate,
|
|
381
|
+
validateStructure,
|
|
382
|
+
validateSemantics,
|
|
383
|
+
validateCompleteness,
|
|
384
|
+
normalizeProposal,
|
|
385
|
+
isValid,
|
|
386
|
+
};
|
|
@@ -0,0 +1,332 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Reality Engine
|
|
3
|
+
*
|
|
4
|
+
* Entry point for the Reality State Engine.
|
|
5
|
+
* Provides a unified API for accessing and monitoring repository reality.
|
|
6
|
+
*
|
|
7
|
+
* Usage:
|
|
8
|
+
* const { reality } = require('./reality');
|
|
9
|
+
*
|
|
10
|
+
* // Get current state
|
|
11
|
+
* const state = reality.getState(projectRoot);
|
|
12
|
+
*
|
|
13
|
+
* // Check if something exists
|
|
14
|
+
* reality.routeExists(state, 'GET', '/api/users');
|
|
15
|
+
* reality.envVarExists(state, 'JWT_SECRET');
|
|
16
|
+
*
|
|
17
|
+
* // Watch for changes
|
|
18
|
+
* const watcher = reality.watch(projectRoot);
|
|
19
|
+
* watcher.on('change', ({ state, changes }) => { ... });
|
|
20
|
+
*/
|
|
21
|
+
|
|
22
|
+
"use strict";
|
|
23
|
+
|
|
24
|
+
const {
|
|
25
|
+
buildRealityState,
|
|
26
|
+
getRealityState,
|
|
27
|
+
invalidateCache,
|
|
28
|
+
routeExists,
|
|
29
|
+
envVarExists,
|
|
30
|
+
fileExists,
|
|
31
|
+
getFilesByDomain,
|
|
32
|
+
getStateSummary,
|
|
33
|
+
classifyFileDomain,
|
|
34
|
+
hashFile,
|
|
35
|
+
} = require("./state");
|
|
36
|
+
|
|
37
|
+
const { RealityWatcher, createWatcher } = require("./watcher");
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* Reality Engine singleton
|
|
41
|
+
*/
|
|
42
|
+
const reality = {
|
|
43
|
+
/**
|
|
44
|
+
* Get the current reality state for a project
|
|
45
|
+
* @param {string} projectRoot - Project root directory
|
|
46
|
+
* @param {Object} options - Options
|
|
47
|
+
* @returns {RealityState} The reality state
|
|
48
|
+
*/
|
|
49
|
+
getState(projectRoot, options = {}) {
|
|
50
|
+
return getRealityState(projectRoot, options);
|
|
51
|
+
},
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Build a fresh reality state (bypasses cache)
|
|
55
|
+
* @param {string} projectRoot - Project root directory
|
|
56
|
+
* @param {Object} options - Options
|
|
57
|
+
* @returns {RealityState} The reality state
|
|
58
|
+
*/
|
|
59
|
+
build(projectRoot, options = {}) {
|
|
60
|
+
return buildRealityState(projectRoot, { ...options, forceRefresh: true });
|
|
61
|
+
},
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* Invalidate the cached reality state
|
|
65
|
+
*/
|
|
66
|
+
invalidate() {
|
|
67
|
+
invalidateCache();
|
|
68
|
+
},
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Create a watcher for reality state changes
|
|
72
|
+
* @param {string} projectRoot - Project root directory
|
|
73
|
+
* @param {Object} options - Watcher options
|
|
74
|
+
* @returns {RealityWatcher} The watcher instance
|
|
75
|
+
*/
|
|
76
|
+
watch(projectRoot, options = {}) {
|
|
77
|
+
const watcher = createWatcher(projectRoot, options);
|
|
78
|
+
return watcher;
|
|
79
|
+
},
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* Check if a route exists in the reality state
|
|
83
|
+
* @param {RealityState} state - Reality state
|
|
84
|
+
* @param {string} method - HTTP method
|
|
85
|
+
* @param {string} path - Route path
|
|
86
|
+
* @returns {boolean} True if route exists
|
|
87
|
+
*/
|
|
88
|
+
routeExists(state, method, path) {
|
|
89
|
+
return routeExists(state, method, path);
|
|
90
|
+
},
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Check if an environment variable exists (is declared)
|
|
94
|
+
* @param {RealityState} state - Reality state
|
|
95
|
+
* @param {string} varName - Variable name
|
|
96
|
+
* @returns {boolean} True if env var is declared
|
|
97
|
+
*/
|
|
98
|
+
envVarExists(state, varName) {
|
|
99
|
+
return envVarExists(state, varName);
|
|
100
|
+
},
|
|
101
|
+
|
|
102
|
+
/**
|
|
103
|
+
* Check if a file exists in the reality state
|
|
104
|
+
* @param {RealityState} state - Reality state
|
|
105
|
+
* @param {string} filePath - File path (relative to project root)
|
|
106
|
+
* @returns {boolean} True if file exists
|
|
107
|
+
*/
|
|
108
|
+
fileExists(state, filePath) {
|
|
109
|
+
return fileExists(state, filePath);
|
|
110
|
+
},
|
|
111
|
+
|
|
112
|
+
/**
|
|
113
|
+
* Get all files in a specific domain
|
|
114
|
+
* @param {RealityState} state - Reality state
|
|
115
|
+
* @param {string} domain - Domain name (auth, payments, routes, etc.)
|
|
116
|
+
* @returns {Array} Array of file objects
|
|
117
|
+
*/
|
|
118
|
+
getFilesByDomain(state, domain) {
|
|
119
|
+
return getFilesByDomain(state, domain);
|
|
120
|
+
},
|
|
121
|
+
|
|
122
|
+
/**
|
|
123
|
+
* Get a summary of the reality state
|
|
124
|
+
* @param {RealityState} state - Reality state
|
|
125
|
+
* @returns {Object} Summary object
|
|
126
|
+
*/
|
|
127
|
+
getSummary(state) {
|
|
128
|
+
return getStateSummary(state);
|
|
129
|
+
},
|
|
130
|
+
|
|
131
|
+
/**
|
|
132
|
+
* Classify a file path into a domain
|
|
133
|
+
* @param {string} filePath - File path
|
|
134
|
+
* @returns {string} Domain name
|
|
135
|
+
*/
|
|
136
|
+
classifyDomain(filePath) {
|
|
137
|
+
return classifyFileDomain(filePath);
|
|
138
|
+
},
|
|
139
|
+
|
|
140
|
+
/**
|
|
141
|
+
* Calculate a file's content hash
|
|
142
|
+
* @param {string} filePath - Absolute file path
|
|
143
|
+
* @returns {string|null} Hash or null if file can't be read
|
|
144
|
+
*/
|
|
145
|
+
hashFile(filePath) {
|
|
146
|
+
return hashFile(filePath);
|
|
147
|
+
},
|
|
148
|
+
|
|
149
|
+
/**
|
|
150
|
+
* Validate assumptions against reality
|
|
151
|
+
* @param {RealityState} state - Reality state
|
|
152
|
+
* @param {Array} assumptions - Array of assumptions to validate
|
|
153
|
+
* @returns {Object} Validation results
|
|
154
|
+
*/
|
|
155
|
+
validateAssumptions(state, assumptions) {
|
|
156
|
+
const results = {
|
|
157
|
+
valid: [],
|
|
158
|
+
invalid: [],
|
|
159
|
+
unknown: [],
|
|
160
|
+
};
|
|
161
|
+
|
|
162
|
+
for (const assumption of assumptions) {
|
|
163
|
+
const result = {
|
|
164
|
+
assumption,
|
|
165
|
+
status: "unknown",
|
|
166
|
+
evidence: null,
|
|
167
|
+
};
|
|
168
|
+
|
|
169
|
+
switch (assumption.type) {
|
|
170
|
+
case "env":
|
|
171
|
+
if (envVarExists(state, assumption.key)) {
|
|
172
|
+
result.status = "valid";
|
|
173
|
+
result.evidence = state.envVars.get(assumption.key);
|
|
174
|
+
} else {
|
|
175
|
+
result.status = "invalid";
|
|
176
|
+
result.evidence = `Environment variable '${assumption.key}' is not declared`;
|
|
177
|
+
}
|
|
178
|
+
break;
|
|
179
|
+
|
|
180
|
+
case "route":
|
|
181
|
+
if (routeExists(state, assumption.method || "GET", assumption.path)) {
|
|
182
|
+
result.status = "valid";
|
|
183
|
+
const route = state.routes.find(r =>
|
|
184
|
+
r.path === assumption.path ||
|
|
185
|
+
r.method.toUpperCase() === (assumption.method || "GET").toUpperCase()
|
|
186
|
+
);
|
|
187
|
+
result.evidence = route;
|
|
188
|
+
} else {
|
|
189
|
+
result.status = "invalid";
|
|
190
|
+
result.evidence = `Route '${assumption.method || "GET"} ${assumption.path}' is not registered`;
|
|
191
|
+
}
|
|
192
|
+
break;
|
|
193
|
+
|
|
194
|
+
case "file":
|
|
195
|
+
if (fileExists(state, assumption.path)) {
|
|
196
|
+
result.status = "valid";
|
|
197
|
+
result.evidence = state.files.get(assumption.path.replace(/\\/g, "/"));
|
|
198
|
+
} else {
|
|
199
|
+
result.status = "invalid";
|
|
200
|
+
result.evidence = `File '${assumption.path}' does not exist`;
|
|
201
|
+
}
|
|
202
|
+
break;
|
|
203
|
+
|
|
204
|
+
case "service":
|
|
205
|
+
const service = state.services.find(s =>
|
|
206
|
+
s.name === assumption.name || s.name === assumption.key
|
|
207
|
+
);
|
|
208
|
+
if (service) {
|
|
209
|
+
result.status = "valid";
|
|
210
|
+
result.evidence = service;
|
|
211
|
+
} else {
|
|
212
|
+
result.status = "invalid";
|
|
213
|
+
result.evidence = `Service '${assumption.name || assumption.key}' is not registered`;
|
|
214
|
+
}
|
|
215
|
+
break;
|
|
216
|
+
|
|
217
|
+
default:
|
|
218
|
+
result.status = "unknown";
|
|
219
|
+
result.evidence = `Unknown assumption type: ${assumption.type}`;
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
if (result.status === "valid") {
|
|
223
|
+
results.valid.push(result);
|
|
224
|
+
} else if (result.status === "invalid") {
|
|
225
|
+
results.invalid.push(result);
|
|
226
|
+
} else {
|
|
227
|
+
results.unknown.push(result);
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
return results;
|
|
232
|
+
},
|
|
233
|
+
|
|
234
|
+
/**
|
|
235
|
+
* Get reality diff between two states
|
|
236
|
+
* @param {RealityState} oldState - Previous state
|
|
237
|
+
* @param {RealityState} newState - Current state
|
|
238
|
+
* @returns {Object} Diff object
|
|
239
|
+
*/
|
|
240
|
+
diff(oldState, newState) {
|
|
241
|
+
const diff = {
|
|
242
|
+
files: {
|
|
243
|
+
added: [],
|
|
244
|
+
removed: [],
|
|
245
|
+
modified: [],
|
|
246
|
+
},
|
|
247
|
+
routes: {
|
|
248
|
+
added: [],
|
|
249
|
+
removed: [],
|
|
250
|
+
},
|
|
251
|
+
envVars: {
|
|
252
|
+
added: [],
|
|
253
|
+
removed: [],
|
|
254
|
+
},
|
|
255
|
+
};
|
|
256
|
+
|
|
257
|
+
// File diff
|
|
258
|
+
const oldFiles = new Set(oldState.files.keys());
|
|
259
|
+
const newFiles = new Set(newState.files.keys());
|
|
260
|
+
|
|
261
|
+
for (const file of newFiles) {
|
|
262
|
+
if (!oldFiles.has(file)) {
|
|
263
|
+
diff.files.added.push(file);
|
|
264
|
+
} else {
|
|
265
|
+
const oldMeta = oldState.files.get(file);
|
|
266
|
+
const newMeta = newState.files.get(file);
|
|
267
|
+
if (oldMeta.hash !== newMeta.hash) {
|
|
268
|
+
diff.files.modified.push(file);
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
for (const file of oldFiles) {
|
|
274
|
+
if (!newFiles.has(file)) {
|
|
275
|
+
diff.files.removed.push(file);
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
// Route diff
|
|
280
|
+
const oldRoutes = new Set(oldState.routes.map(r => `${r.method}:${r.path}`));
|
|
281
|
+
const newRoutes = new Set(newState.routes.map(r => `${r.method}:${r.path}`));
|
|
282
|
+
|
|
283
|
+
for (const route of newState.routes) {
|
|
284
|
+
const key = `${route.method}:${route.path}`;
|
|
285
|
+
if (!oldRoutes.has(key)) {
|
|
286
|
+
diff.routes.added.push(route);
|
|
287
|
+
}
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
for (const route of oldState.routes) {
|
|
291
|
+
const key = `${route.method}:${route.path}`;
|
|
292
|
+
if (!newRoutes.has(key)) {
|
|
293
|
+
diff.routes.removed.push(route);
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
// Env var diff
|
|
298
|
+
const oldEnvVars = new Set(oldState.envVars.keys());
|
|
299
|
+
const newEnvVars = new Set(newState.envVars.keys());
|
|
300
|
+
|
|
301
|
+
for (const varName of newEnvVars) {
|
|
302
|
+
if (!oldEnvVars.has(varName)) {
|
|
303
|
+
diff.envVars.added.push(varName);
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
|
|
307
|
+
for (const varName of oldEnvVars) {
|
|
308
|
+
if (!newEnvVars.has(varName)) {
|
|
309
|
+
diff.envVars.removed.push(varName);
|
|
310
|
+
}
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
return diff;
|
|
314
|
+
},
|
|
315
|
+
};
|
|
316
|
+
|
|
317
|
+
module.exports = {
|
|
318
|
+
reality,
|
|
319
|
+
RealityWatcher,
|
|
320
|
+
createWatcher,
|
|
321
|
+
// Re-export individual functions for direct access
|
|
322
|
+
buildRealityState,
|
|
323
|
+
getRealityState,
|
|
324
|
+
invalidateCache,
|
|
325
|
+
routeExists,
|
|
326
|
+
envVarExists,
|
|
327
|
+
fileExists,
|
|
328
|
+
getFilesByDomain,
|
|
329
|
+
getStateSummary,
|
|
330
|
+
classifyFileDomain,
|
|
331
|
+
hashFile,
|
|
332
|
+
};
|