@newrelic/preflight 0.0.1-pre.1 → 1.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +183 -0
- package/README.md +498 -0
- package/dist/alerts/alert-log.d.ts +24 -0
- package/dist/alerts/alert-log.d.ts.map +1 -0
- package/dist/alerts/alert-log.js +159 -0
- package/dist/alerts/alert-log.js.map +1 -0
- package/dist/alerts/alert-snapshot-collector.d.ts +168 -0
- package/dist/alerts/alert-snapshot-collector.d.ts.map +1 -0
- package/dist/alerts/alert-snapshot-collector.js +243 -0
- package/dist/alerts/alert-snapshot-collector.js.map +1 -0
- package/dist/alerts/local-alert-engine.d.ts +86 -0
- package/dist/alerts/local-alert-engine.d.ts.map +1 -0
- package/dist/alerts/local-alert-engine.js +466 -0
- package/dist/alerts/local-alert-engine.js.map +1 -0
- package/dist/alerts/local-alert-rule.d.ts +439 -0
- package/dist/alerts/local-alert-rule.d.ts.map +1 -0
- package/dist/alerts/local-alert-rule.js +139 -0
- package/dist/alerts/local-alert-rule.js.map +1 -0
- package/dist/alerts/os-notifier.d.ts +39 -0
- package/dist/alerts/os-notifier.d.ts.map +1 -0
- package/dist/alerts/os-notifier.js +170 -0
- package/dist/alerts/os-notifier.js.map +1 -0
- package/dist/alerts/types.d.ts +35 -0
- package/dist/alerts/types.d.ts.map +1 -0
- package/dist/alerts/types.js +8 -0
- package/dist/alerts/types.js.map +1 -0
- package/dist/config.d.ts +169 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +868 -0
- package/dist/config.js.map +1 -0
- package/dist/dashboard/dashboard-server.d.ts +38 -0
- package/dist/dashboard/dashboard-server.d.ts.map +1 -0
- package/dist/dashboard/dashboard-server.js +207 -0
- package/dist/dashboard/dashboard-server.js.map +1 -0
- package/dist/dashboard/index.d.ts +3 -0
- package/dist/dashboard/index.d.ts.map +1 -0
- package/dist/dashboard/index.js +2 -0
- package/dist/dashboard/index.js.map +1 -0
- package/dist/dashboard/live-event-bus.d.ts +99 -0
- package/dist/dashboard/live-event-bus.d.ts.map +1 -0
- package/dist/dashboard/live-event-bus.js +56 -0
- package/dist/dashboard/live-event-bus.js.map +1 -0
- package/dist/dashboard/routes/api-handler.d.ts +122 -0
- package/dist/dashboard/routes/api-handler.d.ts.map +1 -0
- package/dist/dashboard/routes/api-handler.js +1414 -0
- package/dist/dashboard/routes/api-handler.js.map +1 -0
- package/dist/dashboard/routes/replay-analyzer.d.ts +15 -0
- package/dist/dashboard/routes/replay-analyzer.d.ts.map +1 -0
- package/dist/dashboard/routes/replay-analyzer.js +227 -0
- package/dist/dashboard/routes/replay-analyzer.js.map +1 -0
- package/dist/dashboard/routes/sse-handler.d.ts +4 -0
- package/dist/dashboard/routes/sse-handler.d.ts.map +1 -0
- package/dist/dashboard/routes/sse-handler.js +122 -0
- package/dist/dashboard/routes/sse-handler.js.map +1 -0
- package/dist/dashboard/routes/static-handler.d.ts +3 -0
- package/dist/dashboard/routes/static-handler.d.ts.map +1 -0
- package/dist/dashboard/routes/static-handler.js +123 -0
- package/dist/dashboard/routes/static-handler.js.map +1 -0
- package/dist/data/alerts/conditions/01-daily-cost-spike.json +16 -0
- package/dist/data/alerts/conditions/02-low-efficiency-score.json +16 -0
- package/dist/data/alerts/conditions/03-stuck-loop-rate.json +16 -0
- package/dist/data/alerts/conditions/04-anti-pattern-rate.json +16 -0
- package/dist/data/alerts/conditions/05-session-cost-budget.json +16 -0
- package/dist/data/alerts/conditions-personal/01-personal-daily-cost.json +16 -0
- package/dist/data/alerts/conditions-personal/02-personal-session-cost.json +16 -0
- package/dist/data/alerts/conditions-personal/03-personal-low-efficiency.json +16 -0
- package/dist/data/alerts/conditions-personal/04-personal-anti-pattern-rate.json +16 -0
- package/dist/data/alerts/conditions-personal/05-personal-stuck-loop.json +16 -0
- package/dist/data/alerts/policy.json +4 -0
- package/dist/data/dashboards/ai-coding-assistant-manager-view.json +103 -0
- package/dist/data/dashboards/ai-coding-assistant-overview.json +239 -0
- package/dist/data/dashboards/ai-coding-assistant-personal.json +442 -0
- package/dist/data/dashboards/ai-coding-assistant-platform-comparison.json +320 -0
- package/dist/data/dashboards/ai-coding-assistant-security.json +275 -0
- package/dist/data/dashboards/ai-coding-assistant-session-detail.json +296 -0
- package/dist/data/dashboards/ai-coding-assistant-team-view.json +345 -0
- package/dist/deploy/data-paths.d.ts +22 -0
- package/dist/deploy/data-paths.d.ts.map +1 -0
- package/dist/deploy/data-paths.js +69 -0
- package/dist/deploy/data-paths.js.map +1 -0
- package/dist/deploy/deploy-alerts.d.ts +58 -0
- package/dist/deploy/deploy-alerts.d.ts.map +1 -0
- package/dist/deploy/deploy-alerts.js +371 -0
- package/dist/deploy/deploy-alerts.js.map +1 -0
- package/dist/deploy/deploy-dashboards.d.ts +92 -0
- package/dist/deploy/deploy-dashboards.d.ts.map +1 -0
- package/dist/deploy/deploy-dashboards.js +282 -0
- package/dist/deploy/deploy-dashboards.js.map +1 -0
- package/dist/digest/digest-formatter.d.ts +3 -0
- package/dist/digest/digest-formatter.d.ts.map +1 -0
- package/dist/digest/digest-formatter.js +37 -0
- package/dist/digest/digest-formatter.js.map +1 -0
- package/dist/digest/digest-sender.d.ts +2 -0
- package/dist/digest/digest-sender.d.ts.map +1 -0
- package/dist/digest/digest-sender.js +29 -0
- package/dist/digest/digest-sender.js.map +1 -0
- package/dist/hooks/bash-classifier.d.ts +26 -0
- package/dist/hooks/bash-classifier.d.ts.map +1 -0
- package/dist/hooks/bash-classifier.js +409 -0
- package/dist/hooks/bash-classifier.js.map +1 -0
- package/dist/hooks/collector-script.d.ts +47 -0
- package/dist/hooks/collector-script.d.ts.map +1 -0
- package/dist/hooks/collector-script.js +662 -0
- package/dist/hooks/collector-script.js.map +1 -0
- package/dist/hooks/event-processor.d.ts +65 -0
- package/dist/hooks/event-processor.d.ts.map +1 -0
- package/dist/hooks/event-processor.js +342 -0
- package/dist/hooks/event-processor.js.map +1 -0
- package/dist/hooks/index.d.ts +7 -0
- package/dist/hooks/index.d.ts.map +1 -0
- package/dist/hooks/index.js +5 -0
- package/dist/hooks/index.js.map +1 -0
- package/dist/hooks/session-resolver.d.ts +66 -0
- package/dist/hooks/session-resolver.d.ts.map +1 -0
- package/dist/hooks/session-resolver.js +196 -0
- package/dist/hooks/session-resolver.js.map +1 -0
- package/dist/hooks/tool-parsers.d.ts +19 -0
- package/dist/hooks/tool-parsers.d.ts.map +1 -0
- package/dist/hooks/tool-parsers.js +260 -0
- package/dist/hooks/tool-parsers.js.map +1 -0
- package/dist/index.d.ts +107 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +1505 -0
- package/dist/index.js.map +1 -0
- package/dist/install/cli.d.ts +11 -0
- package/dist/install/cli.d.ts.map +1 -0
- package/dist/install/cli.js +365 -0
- package/dist/install/cli.js.map +1 -0
- package/dist/install/index.d.ts +4 -0
- package/dist/install/index.d.ts.map +1 -0
- package/dist/install/index.js +3 -0
- package/dist/install/index.js.map +1 -0
- package/dist/install/install-helper.d.ts +35 -0
- package/dist/install/install-helper.d.ts.map +1 -0
- package/dist/install/install-helper.js +227 -0
- package/dist/install/install-helper.js.map +1 -0
- package/dist/install/key-validator.d.ts +19 -0
- package/dist/install/key-validator.d.ts.map +1 -0
- package/dist/install/key-validator.js +122 -0
- package/dist/install/key-validator.js.map +1 -0
- package/dist/install/migrate.d.ts +12 -0
- package/dist/install/migrate.d.ts.map +1 -0
- package/dist/install/migrate.js +115 -0
- package/dist/install/migrate.js.map +1 -0
- package/dist/install/schedule.d.ts +11 -0
- package/dist/install/schedule.d.ts.map +1 -0
- package/dist/install/schedule.js +114 -0
- package/dist/install/schedule.js.map +1 -0
- package/dist/install/setup-wizard.d.ts +40 -0
- package/dist/install/setup-wizard.d.ts.map +1 -0
- package/dist/install/setup-wizard.js +489 -0
- package/dist/install/setup-wizard.js.map +1 -0
- package/dist/lib/date.d.ts +54 -0
- package/dist/lib/date.d.ts.map +1 -0
- package/dist/lib/date.js +85 -0
- package/dist/lib/date.js.map +1 -0
- package/dist/metrics/anti-patterns.d.ts +62 -0
- package/dist/metrics/anti-patterns.d.ts.map +1 -0
- package/dist/metrics/anti-patterns.js +301 -0
- package/dist/metrics/anti-patterns.js.map +1 -0
- package/dist/metrics/api-failure-tracker.d.ts +82 -0
- package/dist/metrics/api-failure-tracker.d.ts.map +1 -0
- package/dist/metrics/api-failure-tracker.js +202 -0
- package/dist/metrics/api-failure-tracker.js.map +1 -0
- package/dist/metrics/budget-tracker.d.ts +60 -0
- package/dist/metrics/budget-tracker.d.ts.map +1 -0
- package/dist/metrics/budget-tracker.js +130 -0
- package/dist/metrics/budget-tracker.js.map +1 -0
- package/dist/metrics/claudemd-tracker.d.ts +108 -0
- package/dist/metrics/claudemd-tracker.d.ts.map +1 -0
- package/dist/metrics/claudemd-tracker.js +337 -0
- package/dist/metrics/claudemd-tracker.js.map +1 -0
- package/dist/metrics/collaboration-profile.d.ts +65 -0
- package/dist/metrics/collaboration-profile.d.ts.map +1 -0
- package/dist/metrics/collaboration-profile.js +231 -0
- package/dist/metrics/collaboration-profile.js.map +1 -0
- package/dist/metrics/context-composition-tracker.d.ts +74 -0
- package/dist/metrics/context-composition-tracker.d.ts.map +1 -0
- package/dist/metrics/context-composition-tracker.js +202 -0
- package/dist/metrics/context-composition-tracker.js.map +1 -0
- package/dist/metrics/context-tracker.d.ts +78 -0
- package/dist/metrics/context-tracker.d.ts.map +1 -0
- package/dist/metrics/context-tracker.js +222 -0
- package/dist/metrics/context-tracker.js.map +1 -0
- package/dist/metrics/context-window-tracker.d.ts +18 -0
- package/dist/metrics/context-window-tracker.d.ts.map +1 -0
- package/dist/metrics/context-window-tracker.js +35 -0
- package/dist/metrics/context-window-tracker.js.map +1 -0
- package/dist/metrics/cost-forecast.d.ts +36 -0
- package/dist/metrics/cost-forecast.d.ts.map +1 -0
- package/dist/metrics/cost-forecast.js +91 -0
- package/dist/metrics/cost-forecast.js.map +1 -0
- package/dist/metrics/cost-per-outcome.d.ts +102 -0
- package/dist/metrics/cost-per-outcome.d.ts.map +1 -0
- package/dist/metrics/cost-per-outcome.js +266 -0
- package/dist/metrics/cost-per-outcome.js.map +1 -0
- package/dist/metrics/cost-tracker.d.ts +78 -0
- package/dist/metrics/cost-tracker.d.ts.map +1 -0
- package/dist/metrics/cost-tracker.js +169 -0
- package/dist/metrics/cost-tracker.js.map +1 -0
- package/dist/metrics/decision-tracker.d.ts +49 -0
- package/dist/metrics/decision-tracker.d.ts.map +1 -0
- package/dist/metrics/decision-tracker.js +161 -0
- package/dist/metrics/decision-tracker.js.map +1 -0
- package/dist/metrics/efficiency-score.d.ts +80 -0
- package/dist/metrics/efficiency-score.d.ts.map +1 -0
- package/dist/metrics/efficiency-score.js +219 -0
- package/dist/metrics/efficiency-score.js.map +1 -0
- package/dist/metrics/git-efficiency-tracker.d.ts +165 -0
- package/dist/metrics/git-efficiency-tracker.d.ts.map +1 -0
- package/dist/metrics/git-efficiency-tracker.js +1056 -0
- package/dist/metrics/git-efficiency-tracker.js.map +1 -0
- package/dist/metrics/index.d.ts +26 -0
- package/dist/metrics/index.d.ts.map +1 -0
- package/dist/metrics/index.js +14 -0
- package/dist/metrics/index.js.map +1 -0
- package/dist/metrics/instruction-drift-tracker.d.ts +69 -0
- package/dist/metrics/instruction-drift-tracker.d.ts.map +1 -0
- package/dist/metrics/instruction-drift-tracker.js +213 -0
- package/dist/metrics/instruction-drift-tracker.js.map +1 -0
- package/dist/metrics/latency-decomposition.d.ts +50 -0
- package/dist/metrics/latency-decomposition.d.ts.map +1 -0
- package/dist/metrics/latency-decomposition.js +112 -0
- package/dist/metrics/latency-decomposition.js.map +1 -0
- package/dist/metrics/latency-tracker.d.ts +33 -0
- package/dist/metrics/latency-tracker.d.ts.map +1 -0
- package/dist/metrics/latency-tracker.js +93 -0
- package/dist/metrics/latency-tracker.js.map +1 -0
- package/dist/metrics/live-session-registry.d.ts +29 -0
- package/dist/metrics/live-session-registry.d.ts.map +1 -0
- package/dist/metrics/live-session-registry.js +103 -0
- package/dist/metrics/live-session-registry.js.map +1 -0
- package/dist/metrics/model-usage-tracker.d.ts +21 -0
- package/dist/metrics/model-usage-tracker.d.ts.map +1 -0
- package/dist/metrics/model-usage-tracker.js +53 -0
- package/dist/metrics/model-usage-tracker.js.map +1 -0
- package/dist/metrics/percentile.d.ts +5 -0
- package/dist/metrics/percentile.d.ts.map +1 -0
- package/dist/metrics/percentile.js +10 -0
- package/dist/metrics/percentile.js.map +1 -0
- package/dist/metrics/personal-coach.d.ts +47 -0
- package/dist/metrics/personal-coach.d.ts.map +1 -0
- package/dist/metrics/personal-coach.js +241 -0
- package/dist/metrics/personal-coach.js.map +1 -0
- package/dist/metrics/prompt-feedback.d.ts +75 -0
- package/dist/metrics/prompt-feedback.d.ts.map +1 -0
- package/dist/metrics/prompt-feedback.js +286 -0
- package/dist/metrics/prompt-feedback.js.map +1 -0
- package/dist/metrics/proxy-metrics.d.ts +54 -0
- package/dist/metrics/proxy-metrics.d.ts.map +1 -0
- package/dist/metrics/proxy-metrics.js +228 -0
- package/dist/metrics/proxy-metrics.js.map +1 -0
- package/dist/metrics/quality-proxy-tracker.d.ts +51 -0
- package/dist/metrics/quality-proxy-tracker.d.ts.map +1 -0
- package/dist/metrics/quality-proxy-tracker.js +162 -0
- package/dist/metrics/quality-proxy-tracker.js.map +1 -0
- package/dist/metrics/recommendation-engine.d.ts +72 -0
- package/dist/metrics/recommendation-engine.d.ts.map +1 -0
- package/dist/metrics/recommendation-engine.js +207 -0
- package/dist/metrics/recommendation-engine.js.map +1 -0
- package/dist/metrics/retry-detector.d.ts +43 -0
- package/dist/metrics/retry-detector.d.ts.map +1 -0
- package/dist/metrics/retry-detector.js +179 -0
- package/dist/metrics/retry-detector.js.map +1 -0
- package/dist/metrics/session-tracker.d.ts +75 -0
- package/dist/metrics/session-tracker.d.ts.map +1 -0
- package/dist/metrics/session-tracker.js +249 -0
- package/dist/metrics/session-tracker.js.map +1 -0
- package/dist/metrics/task-completion-tracker.d.ts +15 -0
- package/dist/metrics/task-completion-tracker.d.ts.map +1 -0
- package/dist/metrics/task-completion-tracker.js +27 -0
- package/dist/metrics/task-completion-tracker.js.map +1 -0
- package/dist/metrics/task-detector.d.ts +84 -0
- package/dist/metrics/task-detector.d.ts.map +1 -0
- package/dist/metrics/task-detector.js +302 -0
- package/dist/metrics/task-detector.js.map +1 -0
- package/dist/metrics/tool-selection-scorer.d.ts +39 -0
- package/dist/metrics/tool-selection-scorer.d.ts.map +1 -0
- package/dist/metrics/tool-selection-scorer.js +193 -0
- package/dist/metrics/tool-selection-scorer.js.map +1 -0
- package/dist/metrics/trend-analyzer.d.ts +92 -0
- package/dist/metrics/trend-analyzer.d.ts.map +1 -0
- package/dist/metrics/trend-analyzer.js +293 -0
- package/dist/metrics/trend-analyzer.js.map +1 -0
- package/dist/metrics/turn-cost-attributor.d.ts +41 -0
- package/dist/metrics/turn-cost-attributor.d.ts.map +1 -0
- package/dist/metrics/turn-cost-attributor.js +118 -0
- package/dist/metrics/turn-cost-attributor.js.map +1 -0
- package/dist/metrics/turn-tracker.d.ts +49 -0
- package/dist/metrics/turn-tracker.d.ts.map +1 -0
- package/dist/metrics/turn-tracker.js +192 -0
- package/dist/metrics/turn-tracker.js.map +1 -0
- package/dist/platforms/amazon-q-adapter.d.ts +10 -0
- package/dist/platforms/amazon-q-adapter.d.ts.map +1 -0
- package/dist/platforms/amazon-q-adapter.js +75 -0
- package/dist/platforms/amazon-q-adapter.js.map +1 -0
- package/dist/platforms/claude-code-adapter.d.ts +10 -0
- package/dist/platforms/claude-code-adapter.d.ts.map +1 -0
- package/dist/platforms/claude-code-adapter.js +48 -0
- package/dist/platforms/claude-code-adapter.js.map +1 -0
- package/dist/platforms/continue-adapter.d.ts +10 -0
- package/dist/platforms/continue-adapter.d.ts.map +1 -0
- package/dist/platforms/continue-adapter.js +73 -0
- package/dist/platforms/continue-adapter.js.map +1 -0
- package/dist/platforms/copilot-adapter.d.ts +37 -0
- package/dist/platforms/copilot-adapter.d.ts.map +1 -0
- package/dist/platforms/copilot-adapter.js +66 -0
- package/dist/platforms/copilot-adapter.js.map +1 -0
- package/dist/platforms/cursor-adapter.d.ts +10 -0
- package/dist/platforms/cursor-adapter.d.ts.map +1 -0
- package/dist/platforms/cursor-adapter.js +60 -0
- package/dist/platforms/cursor-adapter.js.map +1 -0
- package/dist/platforms/generic-mcp-adapter.d.ts +113 -0
- package/dist/platforms/generic-mcp-adapter.d.ts.map +1 -0
- package/dist/platforms/generic-mcp-adapter.js +139 -0
- package/dist/platforms/generic-mcp-adapter.js.map +1 -0
- package/dist/platforms/index.d.ts +15 -0
- package/dist/platforms/index.d.ts.map +1 -0
- package/dist/platforms/index.js +12 -0
- package/dist/platforms/index.js.map +1 -0
- package/dist/platforms/platform-registry.d.ts +11 -0
- package/dist/platforms/platform-registry.d.ts.map +1 -0
- package/dist/platforms/platform-registry.js +54 -0
- package/dist/platforms/platform-registry.js.map +1 -0
- package/dist/platforms/types.d.ts +36 -0
- package/dist/platforms/types.d.ts.map +1 -0
- package/dist/platforms/types.js +2 -0
- package/dist/platforms/types.js.map +1 -0
- package/dist/platforms/windsurf-adapter.d.ts +10 -0
- package/dist/platforms/windsurf-adapter.d.ts.map +1 -0
- package/dist/platforms/windsurf-adapter.js +63 -0
- package/dist/platforms/windsurf-adapter.js.map +1 -0
- package/dist/platforms/zed-adapter.d.ts +10 -0
- package/dist/platforms/zed-adapter.d.ts.map +1 -0
- package/dist/platforms/zed-adapter.js +72 -0
- package/dist/platforms/zed-adapter.js.map +1 -0
- package/dist/proxy/index.d.ts +7 -0
- package/dist/proxy/index.d.ts.map +1 -0
- package/dist/proxy/index.js +5 -0
- package/dist/proxy/index.js.map +1 -0
- package/dist/proxy/otlp-receiver.d.ts +28 -0
- package/dist/proxy/otlp-receiver.d.ts.map +1 -0
- package/dist/proxy/otlp-receiver.js +319 -0
- package/dist/proxy/otlp-receiver.js.map +1 -0
- package/dist/proxy/proxy-manager.d.ts +47 -0
- package/dist/proxy/proxy-manager.d.ts.map +1 -0
- package/dist/proxy/proxy-manager.js +338 -0
- package/dist/proxy/proxy-manager.js.map +1 -0
- package/dist/proxy/types.d.ts +72 -0
- package/dist/proxy/types.d.ts.map +1 -0
- package/dist/proxy/types.js +33 -0
- package/dist/proxy/types.js.map +1 -0
- package/dist/proxy/upstream-http.d.ts +26 -0
- package/dist/proxy/upstream-http.d.ts.map +1 -0
- package/dist/proxy/upstream-http.js +209 -0
- package/dist/proxy/upstream-http.js.map +1 -0
- package/dist/proxy/upstream-stdio.d.ts +25 -0
- package/dist/proxy/upstream-stdio.d.ts.map +1 -0
- package/dist/proxy/upstream-stdio.js +256 -0
- package/dist/proxy/upstream-stdio.js.map +1 -0
- package/dist/security/audit-trail.d.ts +74 -0
- package/dist/security/audit-trail.d.ts.map +1 -0
- package/dist/security/audit-trail.js +338 -0
- package/dist/security/audit-trail.js.map +1 -0
- package/dist/security/index.d.ts +5 -0
- package/dist/security/index.d.ts.map +1 -0
- package/dist/security/index.js +4 -0
- package/dist/security/index.js.map +1 -0
- package/dist/security/ssrf.d.ts +2 -0
- package/dist/security/ssrf.d.ts.map +1 -0
- package/dist/security/ssrf.js +126 -0
- package/dist/security/ssrf.js.map +1 -0
- package/dist/server.d.ts +14 -0
- package/dist/server.d.ts.map +1 -0
- package/dist/server.js +117 -0
- package/dist/server.js.map +1 -0
- package/dist/shared/__test-utils__/log-output.d.ts +49 -0
- package/dist/shared/__test-utils__/log-output.d.ts.map +1 -0
- package/dist/shared/__test-utils__/log-output.js +38 -0
- package/dist/shared/__test-utils__/log-output.js.map +1 -0
- package/dist/shared/config.d.ts +56 -0
- package/dist/shared/config.d.ts.map +1 -0
- package/dist/shared/config.js +290 -0
- package/dist/shared/config.js.map +1 -0
- package/dist/shared/errors.d.ts +139 -0
- package/dist/shared/errors.d.ts.map +1 -0
- package/dist/shared/errors.js +406 -0
- package/dist/shared/errors.js.map +1 -0
- package/dist/shared/events/factory.d.ts +143 -0
- package/dist/shared/events/factory.d.ts.map +1 -0
- package/dist/shared/events/factory.js +351 -0
- package/dist/shared/events/factory.js.map +1 -0
- package/dist/shared/events/index.d.ts +6 -0
- package/dist/shared/events/index.d.ts.map +1 -0
- package/dist/shared/events/index.js +3 -0
- package/dist/shared/events/index.js.map +1 -0
- package/dist/shared/events/serialize.d.ts +87 -0
- package/dist/shared/events/serialize.d.ts.map +1 -0
- package/dist/shared/events/serialize.js +510 -0
- package/dist/shared/events/serialize.js.map +1 -0
- package/dist/shared/events/types.d.ts +139 -0
- package/dist/shared/events/types.d.ts.map +1 -0
- package/dist/shared/events/types.js +2 -0
- package/dist/shared/events/types.js.map +1 -0
- package/dist/shared/harvest/event-buffer.d.ts +59 -0
- package/dist/shared/harvest/event-buffer.d.ts.map +1 -0
- package/dist/shared/harvest/event-buffer.js +100 -0
- package/dist/shared/harvest/event-buffer.js.map +1 -0
- package/dist/shared/harvest/harvest-scheduler.d.ts +200 -0
- package/dist/shared/harvest/harvest-scheduler.d.ts.map +1 -0
- package/dist/shared/harvest/harvest-scheduler.js +647 -0
- package/dist/shared/harvest/harvest-scheduler.js.map +1 -0
- package/dist/shared/harvest/index.d.ts +7 -0
- package/dist/shared/harvest/index.d.ts.map +1 -0
- package/dist/shared/harvest/index.js +4 -0
- package/dist/shared/harvest/index.js.map +1 -0
- package/dist/shared/harvest/metric-aggregator.d.ts +115 -0
- package/dist/shared/harvest/metric-aggregator.d.ts.map +1 -0
- package/dist/shared/harvest/metric-aggregator.js +247 -0
- package/dist/shared/harvest/metric-aggregator.js.map +1 -0
- package/dist/shared/index.d.ts +22 -0
- package/dist/shared/index.d.ts.map +1 -0
- package/dist/shared/index.js +13 -0
- package/dist/shared/index.js.map +1 -0
- package/dist/shared/logger.d.ts +57 -0
- package/dist/shared/logger.d.ts.map +1 -0
- package/dist/shared/logger.js +166 -0
- package/dist/shared/logger.js.map +1 -0
- package/dist/shared/pricing-data.d.ts +4 -0
- package/dist/shared/pricing-data.d.ts.map +1 -0
- package/dist/shared/pricing-data.js +473 -0
- package/dist/shared/pricing-data.js.map +1 -0
- package/dist/shared/pricing.d.ts +148 -0
- package/dist/shared/pricing.d.ts.map +1 -0
- package/dist/shared/pricing.js +528 -0
- package/dist/shared/pricing.js.map +1 -0
- package/dist/shared/redact.d.ts +33 -0
- package/dist/shared/redact.d.ts.map +1 -0
- package/dist/shared/redact.js +110 -0
- package/dist/shared/redact.js.map +1 -0
- package/dist/shared/timing.d.ts +96 -0
- package/dist/shared/timing.d.ts.map +1 -0
- package/dist/shared/timing.js +173 -0
- package/dist/shared/timing.js.map +1 -0
- package/dist/shared/tokens.d.ts +145 -0
- package/dist/shared/tokens.d.ts.map +1 -0
- package/dist/shared/tokens.js +492 -0
- package/dist/shared/tokens.js.map +1 -0
- package/dist/shared/transport/events-api.d.ts +14 -0
- package/dist/shared/transport/events-api.d.ts.map +1 -0
- package/dist/shared/transport/events-api.js +29 -0
- package/dist/shared/transport/events-api.js.map +1 -0
- package/dist/shared/transport/http-client.d.ts +49 -0
- package/dist/shared/transport/http-client.d.ts.map +1 -0
- package/dist/shared/transport/http-client.js +381 -0
- package/dist/shared/transport/http-client.js.map +1 -0
- package/dist/shared/transport/index.d.ts +10 -0
- package/dist/shared/transport/index.d.ts.map +1 -0
- package/dist/shared/transport/index.js +6 -0
- package/dist/shared/transport/index.js.map +1 -0
- package/dist/shared/transport/logs-api.d.ts +29 -0
- package/dist/shared/transport/logs-api.d.ts.map +1 -0
- package/dist/shared/transport/logs-api.js +40 -0
- package/dist/shared/transport/logs-api.js.map +1 -0
- package/dist/shared/transport/metric-api.d.ts +9 -0
- package/dist/shared/transport/metric-api.d.ts.map +1 -0
- package/dist/shared/transport/metric-api.js +39 -0
- package/dist/shared/transport/metric-api.js.map +1 -0
- package/dist/shared/transport/otlp-event-bridge.d.ts +22 -0
- package/dist/shared/transport/otlp-event-bridge.d.ts.map +1 -0
- package/dist/shared/transport/otlp-event-bridge.js +50 -0
- package/dist/shared/transport/otlp-event-bridge.js.map +1 -0
- package/dist/shared/transport/otlp-shared.d.ts +14 -0
- package/dist/shared/transport/otlp-shared.d.ts.map +1 -0
- package/dist/shared/transport/otlp-shared.js +49 -0
- package/dist/shared/transport/otlp-shared.js.map +1 -0
- package/dist/shared/transport/otlp-transport.d.ts +58 -0
- package/dist/shared/transport/otlp-transport.d.ts.map +1 -0
- package/dist/shared/transport/otlp-transport.js +236 -0
- package/dist/shared/transport/otlp-transport.js.map +1 -0
- package/dist/shared/transport/types.d.ts +129 -0
- package/dist/shared/transport/types.d.ts.map +1 -0
- package/dist/shared/transport/types.js +2 -0
- package/dist/shared/transport/types.js.map +1 -0
- package/dist/shared/version.d.ts +2 -0
- package/dist/shared/version.d.ts.map +1 -0
- package/dist/shared/version.js +2 -0
- package/dist/shared/version.js.map +1 -0
- package/dist/storage/index.d.ts +7 -0
- package/dist/storage/index.d.ts.map +1 -0
- package/dist/storage/index.js +4 -0
- package/dist/storage/index.js.map +1 -0
- package/dist/storage/local-store.d.ts +153 -0
- package/dist/storage/local-store.d.ts.map +1 -0
- package/dist/storage/local-store.js +719 -0
- package/dist/storage/local-store.js.map +1 -0
- package/dist/storage/retention.d.ts +2 -0
- package/dist/storage/retention.d.ts.map +1 -0
- package/dist/storage/retention.js +53 -0
- package/dist/storage/retention.js.map +1 -0
- package/dist/storage/session-store.d.ts +97 -0
- package/dist/storage/session-store.d.ts.map +1 -0
- package/dist/storage/session-store.js +391 -0
- package/dist/storage/session-store.js.map +1 -0
- package/dist/storage/types.d.ts +64 -0
- package/dist/storage/types.d.ts.map +1 -0
- package/dist/storage/types.js +2 -0
- package/dist/storage/types.js.map +1 -0
- package/dist/storage/weekly-summary.d.ts +61 -0
- package/dist/storage/weekly-summary.d.ts.map +1 -0
- package/dist/storage/weekly-summary.js +243 -0
- package/dist/storage/weekly-summary.js.map +1 -0
- package/dist/tools/analytics-tools.d.ts +101 -0
- package/dist/tools/analytics-tools.d.ts.map +1 -0
- package/dist/tools/analytics-tools.js +71 -0
- package/dist/tools/analytics-tools.js.map +1 -0
- package/dist/tools/cost-tools.d.ts +121 -0
- package/dist/tools/cost-tools.d.ts.map +1 -0
- package/dist/tools/cost-tools.js +174 -0
- package/dist/tools/cost-tools.js.map +1 -0
- package/dist/tools/cross-session-tools.d.ts +376 -0
- package/dist/tools/cross-session-tools.d.ts.map +1 -0
- package/dist/tools/cross-session-tools.js +820 -0
- package/dist/tools/cross-session-tools.js.map +1 -0
- package/dist/tools/extended-analytics-tools.d.ts +164 -0
- package/dist/tools/extended-analytics-tools.d.ts.map +1 -0
- package/dist/tools/extended-analytics-tools.js +121 -0
- package/dist/tools/extended-analytics-tools.js.map +1 -0
- package/dist/tools/index.d.ts +7 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/tools/index.js +4 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/session-stats.d.ts +162 -0
- package/dist/tools/session-stats.d.ts.map +1 -0
- package/dist/tools/session-stats.js +1054 -0
- package/dist/tools/session-stats.js.map +1 -0
- package/dist/tools/workflow-tools.d.ts +126 -0
- package/dist/tools/workflow-tools.d.ts.map +1 -0
- package/dist/tools/workflow-tools.js +274 -0
- package/dist/tools/workflow-tools.js.map +1 -0
- package/dist/tracing/mcp-tracer.d.ts +4 -0
- package/dist/tracing/mcp-tracer.d.ts.map +1 -0
- package/dist/tracing/mcp-tracer.js +14 -0
- package/dist/tracing/mcp-tracer.js.map +1 -0
- package/dist/tracing/session-span.d.ts +14 -0
- package/dist/tracing/session-span.d.ts.map +1 -0
- package/dist/tracing/session-span.js +53 -0
- package/dist/tracing/session-span.js.map +1 -0
- package/dist/tracing/task-span-tracker.d.ts +11 -0
- package/dist/tracing/task-span-tracker.d.ts.map +1 -0
- package/dist/tracing/task-span-tracker.js +59 -0
- package/dist/tracing/task-span-tracker.js.map +1 -0
- package/dist/tracing/tool-call-span.d.ts +4 -0
- package/dist/tracing/tool-call-span.d.ts.map +1 -0
- package/dist/tracing/tool-call-span.js +60 -0
- package/dist/tracing/tool-call-span.js.map +1 -0
- package/dist/transport/index.d.ts +3 -0
- package/dist/transport/index.d.ts.map +1 -0
- package/dist/transport/index.js +2 -0
- package/dist/transport/index.js.map +1 -0
- package/dist/transport/log-ingest.d.ts +42 -0
- package/dist/transport/log-ingest.d.ts.map +1 -0
- package/dist/transport/log-ingest.js +151 -0
- package/dist/transport/log-ingest.js.map +1 -0
- package/dist/transport/nr-ingest.d.ts +171 -0
- package/dist/transport/nr-ingest.d.ts.map +1 -0
- package/dist/transport/nr-ingest.js +659 -0
- package/dist/transport/nr-ingest.js.map +1 -0
- package/dist/types.d.ts +45 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +2 -0
- package/dist/types.js.map +1 -0
- package/dist/web/assets/index-BrL281N-.css +2 -0
- package/dist/web/assets/index-CcaYZzXm.js +42 -0
- package/dist/web/favicon.svg +15 -0
- package/dist/web/index.html +15 -0
- package/examples/local-alert-rules.json +106 -0
- package/package.json +129 -1
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import type { AlertEvent } from '../dashboard/live-event-bus.js';
|
|
2
|
+
import type { SnapshotWindowSpec } from './alert-snapshot-collector.js';
|
|
3
|
+
import type { OsNotifier } from './os-notifier.js';
|
|
4
|
+
import type { LocalAlertRule } from './local-alert-rule.js';
|
|
5
|
+
export type { AlertSnapshot } from './alert-snapshot-collector.js';
|
|
6
|
+
import type { AlertSnapshot } from './alert-snapshot-collector.js';
|
|
7
|
+
export interface LocalAlertEngineOptions {
|
|
8
|
+
readonly clock?: () => number;
|
|
9
|
+
/**
|
|
10
|
+
* Optional OS notifier. When present AND `osNotificationsEnabled` is true
|
|
11
|
+
* AND the firing rule's `channels` includes `'os'`, the engine fires an
|
|
12
|
+
* out-of-band OS notification. Notifier failures are swallowed by
|
|
13
|
+
* OsNotifier itself; this engine never awaits the call.
|
|
14
|
+
*/
|
|
15
|
+
readonly osNotifier?: OsNotifier;
|
|
16
|
+
/**
|
|
17
|
+
* Master switch from `config.alerts.osNotifications`. When false (the
|
|
18
|
+
* default) OS notifications are suppressed even if a rule opts into the
|
|
19
|
+
* `'os'` channel.
|
|
20
|
+
*/
|
|
21
|
+
readonly osNotificationsEnabled?: boolean;
|
|
22
|
+
}
|
|
23
|
+
export declare class LocalAlertEngine {
|
|
24
|
+
private readonly clock;
|
|
25
|
+
private rules;
|
|
26
|
+
private readonly state;
|
|
27
|
+
private onAlert;
|
|
28
|
+
private readonly osNotifier;
|
|
29
|
+
private readonly osNotificationsEnabled;
|
|
30
|
+
constructor(opts?: LocalAlertEngineOptions);
|
|
31
|
+
loadRules(rules: readonly LocalAlertRule[]): void;
|
|
32
|
+
setOnAlert(callback: (event: AlertEvent) => void): void;
|
|
33
|
+
evaluate(snapshot: AlertSnapshot, now: number): readonly AlertEvent[];
|
|
34
|
+
/**
|
|
35
|
+
* Fire an out-of-band OS notification for a firing event when both the
|
|
36
|
+
* global `osNotificationsEnabled` flag is true AND the rule opts into the
|
|
37
|
+
* `'os'` channel. `cleared` events do not trigger notifications — clearing
|
|
38
|
+
* is a quiet UX. The call is fire-and-forget; OsNotifier swallows its own
|
|
39
|
+
* errors.
|
|
40
|
+
*/
|
|
41
|
+
private maybeFireOsNotification;
|
|
42
|
+
private evaluateRule;
|
|
43
|
+
/**
|
|
44
|
+
* Common state machine for the non-budget rule types. Caller has already
|
|
45
|
+
* computed the rule's current numeric `value`; if `value` is null the
|
|
46
|
+
* rule cannot be evaluated this cycle (e.g. no efficiency score yet) and
|
|
47
|
+
* neither fires nor clears.
|
|
48
|
+
*
|
|
49
|
+
* Deduplication semantics: when a rule has just cleared, it cannot
|
|
50
|
+
* re-fire until `deduplicateSeconds` after `lastClearedAt`. While in the
|
|
51
|
+
* dedupe window, the engine suppresses the firing event AND keeps the
|
|
52
|
+
* state machine at `'idle'` — so on the next evaluation past the window,
|
|
53
|
+
* a still-true condition will fire normally.
|
|
54
|
+
*/
|
|
55
|
+
private evaluateThresholdRule;
|
|
56
|
+
/**
|
|
57
|
+
* Special-case for `efficiency.below`: the trigger condition only counts
|
|
58
|
+
* after it's been continuously true for `windowSeconds`. We track when
|
|
59
|
+
* the condition first became true (`firstBelowAt`); the rule can only
|
|
60
|
+
* fire once `now - firstBelowAt >= windowSeconds * 1000`.
|
|
61
|
+
*/
|
|
62
|
+
private evaluateEfficiencyBelowRule;
|
|
63
|
+
private applyThresholdState;
|
|
64
|
+
/**
|
|
65
|
+
* Cost windows are session/today/week cumulative — not a true rolling
|
|
66
|
+
* window. The engine reads whichever bucket the rule names; a real
|
|
67
|
+
* rolling-N-second cost calculation is not yet implemented.
|
|
68
|
+
*/
|
|
69
|
+
private computeCostWindowValue;
|
|
70
|
+
private computeAntiPatternCountValue;
|
|
71
|
+
private computeLatencyValue;
|
|
72
|
+
private computeToolFailureValue;
|
|
73
|
+
private evaluateBudgetRule;
|
|
74
|
+
private getOrInitState;
|
|
75
|
+
private periodKey;
|
|
76
|
+
getFiringRuleIds(): readonly string[];
|
|
77
|
+
/**
|
|
78
|
+
* Inspect the loaded rule set and return the windows the snapshot
|
|
79
|
+
* collector needs to populate. Each entry is one (kind, key, windowMs)
|
|
80
|
+
* the engine will look for in `evaluate()`. Duplicates are de-duplicated.
|
|
81
|
+
*/
|
|
82
|
+
getRequiredWindows(): readonly SnapshotWindowSpec[];
|
|
83
|
+
/** Exposed for Phase 2 wiring; returns the current monotonic clock reading. */
|
|
84
|
+
now(): number;
|
|
85
|
+
}
|
|
86
|
+
//# sourceMappingURL=local-alert-engine.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-alert-engine.d.ts","sourceRoot":"","sources":["../../src/alerts/local-alert-engine.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gCAAgC,CAAC;AACjE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,+BAA+B,CAAC;AACxE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AACnD,OAAO,KAAK,EACV,cAAc,EAUf,MAAM,uBAAuB,CAAC;AAU/B,YAAY,EAAE,aAAa,EAAE,MAAM,+BAA+B,CAAC;AACnE,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,+BAA+B,CAAC;AAEnE,MAAM,WAAW,uBAAuB;IACtC,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,MAAM,CAAC;IAC9B;;;;;OAKG;IACH,QAAQ,CAAC,UAAU,CAAC,EAAE,UAAU,CAAC;IACjC;;;;OAIG;IACH,QAAQ,CAAC,sBAAsB,CAAC,EAAE,OAAO,CAAC;CAC3C;AA4DD,qBAAa,gBAAgB;IAC3B,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAe;IACrC,OAAO,CAAC,KAAK,CAAwB;IACrC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAgC;IACtD,OAAO,CAAC,OAAO,CAA4C;IAC3D,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAyB;IACpD,OAAO,CAAC,QAAQ,CAAC,sBAAsB,CAAU;gBAErC,IAAI,GAAE,uBAA4B;IAM9C,SAAS,CAAC,KAAK,EAAE,SAAS,cAAc,EAAE,GAAG,IAAI;IAkBjD,UAAU,CAAC,QAAQ,EAAE,CAAC,KAAK,EAAE,UAAU,KAAK,IAAI,GAAG,IAAI;IAIvD,QAAQ,CAAC,QAAQ,EAAE,aAAa,EAAE,GAAG,EAAE,MAAM,GAAG,SAAS,UAAU,EAAE;IAqBrE;;;;;;OAMG;IACH,OAAO,CAAC,uBAAuB;IAQ/B,OAAO,CAAC,YAAY;IA4BpB;;;;;;;;;;;OAWG;IACH,OAAO,CAAC,qBAAqB;IAU7B;;;;;OAKG;IACH,OAAO,CAAC,2BAA2B;IAsBnC,OAAO,CAAC,mBAAmB;IA2D3B;;;;OAIG;IACH,OAAO,CAAC,sBAAsB;IAW9B,OAAO,CAAC,4BAA4B;IAiBpC,OAAO,CAAC,mBAAmB;IA0B3B,OAAO,CAAC,uBAAuB;IAQ/B,OAAO,CAAC,kBAAkB;IAgG1B,OAAO,CAAC,cAAc;IAStB,OAAO,CAAC,SAAS;IAsBjB,gBAAgB,IAAI,SAAS,MAAM,EAAE;IAQrC;;;;OAIG;IACH,kBAAkB,IAAI,SAAS,kBAAkB,EAAE;IAyBnD,+EAA+E;IAC/E,GAAG,IAAI,MAAM;CAGd"}
|
|
@@ -0,0 +1,466 @@
|
|
|
1
|
+
import { createLogger } from '../shared/index.js';
|
|
2
|
+
const logger = createLogger('local-alert-engine');
|
|
3
|
+
function budgetPeriodForRule(rule) {
|
|
4
|
+
switch (rule.type) {
|
|
5
|
+
case 'budget.session':
|
|
6
|
+
return 'session';
|
|
7
|
+
case 'budget.daily':
|
|
8
|
+
return 'daily';
|
|
9
|
+
case 'budget.weekly':
|
|
10
|
+
return 'weekly';
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
// ---------------------------------------------------------------------------
|
|
14
|
+
// Operator helpers
|
|
15
|
+
// ---------------------------------------------------------------------------
|
|
16
|
+
function compareOp(value, threshold, op) {
|
|
17
|
+
switch (op) {
|
|
18
|
+
case 'above':
|
|
19
|
+
return value > threshold;
|
|
20
|
+
case 'below':
|
|
21
|
+
return value < threshold;
|
|
22
|
+
case 'above_or_equals':
|
|
23
|
+
return value >= threshold;
|
|
24
|
+
case 'below_or_equals':
|
|
25
|
+
return value <= threshold;
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
// ---------------------------------------------------------------------------
|
|
29
|
+
// Engine
|
|
30
|
+
// ---------------------------------------------------------------------------
|
|
31
|
+
export class LocalAlertEngine {
|
|
32
|
+
clock;
|
|
33
|
+
rules = [];
|
|
34
|
+
state = new Map();
|
|
35
|
+
onAlert;
|
|
36
|
+
osNotifier;
|
|
37
|
+
osNotificationsEnabled;
|
|
38
|
+
constructor(opts = {}) {
|
|
39
|
+
this.clock = opts.clock ?? (() => Date.now());
|
|
40
|
+
this.osNotifier = opts.osNotifier;
|
|
41
|
+
this.osNotificationsEnabled = opts.osNotificationsEnabled === true;
|
|
42
|
+
}
|
|
43
|
+
loadRules(rules) {
|
|
44
|
+
// Atomic swap: replace rule list and prune state for rules that no longer
|
|
45
|
+
// exist. Existing-rule state is preserved so a rule that was firing stays
|
|
46
|
+
// firing across reloads.
|
|
47
|
+
const idsAfter = new Set(rules.map((r) => r.id));
|
|
48
|
+
for (const id of [...this.state.keys()]) {
|
|
49
|
+
if (!idsAfter.has(id))
|
|
50
|
+
this.state.delete(id);
|
|
51
|
+
}
|
|
52
|
+
this.rules = [...rules];
|
|
53
|
+
// Note: the warning about cost.window today/week rules
|
|
54
|
+
// lives in loadAlertRulesFromDisk (src/index.ts) so it fires once
|
|
55
|
+
// per disk load with the rule id and exact costPeriod inline. We
|
|
56
|
+
// deliberately don't duplicate it here — programmatic callers (tests,
|
|
57
|
+
// future code) get the rule loaded without stderr noise; the user-
|
|
58
|
+
// facing path that reads rules.json still surfaces the warning.
|
|
59
|
+
logger.debug('Loaded alert rules', { count: this.rules.length });
|
|
60
|
+
}
|
|
61
|
+
setOnAlert(callback) {
|
|
62
|
+
this.onAlert = callback;
|
|
63
|
+
}
|
|
64
|
+
evaluate(snapshot, now) {
|
|
65
|
+
if (this.rules.length === 0)
|
|
66
|
+
return [];
|
|
67
|
+
const emitted = [];
|
|
68
|
+
for (const rule of this.rules) {
|
|
69
|
+
if (!rule.enabled)
|
|
70
|
+
continue;
|
|
71
|
+
const events = this.evaluateRule(rule, snapshot, now);
|
|
72
|
+
for (const ev of events) {
|
|
73
|
+
emitted.push(ev);
|
|
74
|
+
try {
|
|
75
|
+
this.onAlert?.(ev);
|
|
76
|
+
}
|
|
77
|
+
catch (err) {
|
|
78
|
+
logger.error('onAlert callback threw', { error: String(err), ruleId: rule.id });
|
|
79
|
+
}
|
|
80
|
+
this.maybeFireOsNotification(rule, ev);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return emitted;
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Fire an out-of-band OS notification for a firing event when both the
|
|
87
|
+
* global `osNotificationsEnabled` flag is true AND the rule opts into the
|
|
88
|
+
* `'os'` channel. `cleared` events do not trigger notifications — clearing
|
|
89
|
+
* is a quiet UX. The call is fire-and-forget; OsNotifier swallows its own
|
|
90
|
+
* errors.
|
|
91
|
+
*/
|
|
92
|
+
maybeFireOsNotification(rule, ev) {
|
|
93
|
+
if (!this.osNotifier)
|
|
94
|
+
return;
|
|
95
|
+
if (!this.osNotificationsEnabled)
|
|
96
|
+
return;
|
|
97
|
+
if (ev.state !== 'firing')
|
|
98
|
+
return;
|
|
99
|
+
if (!rule.channels.includes('os'))
|
|
100
|
+
return;
|
|
101
|
+
void this.osNotifier.notify({ title: ev.title, body: ev.description });
|
|
102
|
+
}
|
|
103
|
+
evaluateRule(rule, snapshot, now) {
|
|
104
|
+
// Exhaustive switch so TS catches missing rule-type handlers.
|
|
105
|
+
switch (rule.type) {
|
|
106
|
+
case 'budget.session':
|
|
107
|
+
case 'budget.daily':
|
|
108
|
+
case 'budget.weekly':
|
|
109
|
+
return this.evaluateBudgetRule(rule, snapshot, now);
|
|
110
|
+
case 'cost.window':
|
|
111
|
+
return this.evaluateThresholdRule(rule, this.computeCostWindowValue(rule, snapshot), now);
|
|
112
|
+
case 'efficiency.below':
|
|
113
|
+
return this.evaluateEfficiencyBelowRule(rule, snapshot, now);
|
|
114
|
+
case 'antipattern.count':
|
|
115
|
+
return this.evaluateThresholdRule(rule, this.computeAntiPatternCountValue(rule, snapshot), now);
|
|
116
|
+
case 'latency.percentile':
|
|
117
|
+
return this.evaluateThresholdRule(rule, this.computeLatencyValue(rule, snapshot), now);
|
|
118
|
+
case 'tool.failure':
|
|
119
|
+
return this.evaluateThresholdRule(rule, this.computeToolFailureValue(rule, snapshot), now);
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
// ---------------------------------------------------------------------------
|
|
123
|
+
// Threshold-rule core
|
|
124
|
+
// ---------------------------------------------------------------------------
|
|
125
|
+
/**
|
|
126
|
+
* Common state machine for the non-budget rule types. Caller has already
|
|
127
|
+
* computed the rule's current numeric `value`; if `value` is null the
|
|
128
|
+
* rule cannot be evaluated this cycle (e.g. no efficiency score yet) and
|
|
129
|
+
* neither fires nor clears.
|
|
130
|
+
*
|
|
131
|
+
* Deduplication semantics: when a rule has just cleared, it cannot
|
|
132
|
+
* re-fire until `deduplicateSeconds` after `lastClearedAt`. While in the
|
|
133
|
+
* dedupe window, the engine suppresses the firing event AND keeps the
|
|
134
|
+
* state machine at `'idle'` — so on the next evaluation past the window,
|
|
135
|
+
* a still-true condition will fire normally.
|
|
136
|
+
*/
|
|
137
|
+
evaluateThresholdRule(rule, value, now) {
|
|
138
|
+
if (value === null)
|
|
139
|
+
return [];
|
|
140
|
+
const triggered = compareOp(value, rule.threshold, rule.operator);
|
|
141
|
+
return this.applyThresholdState(rule, value, triggered, now);
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Special-case for `efficiency.below`: the trigger condition only counts
|
|
145
|
+
* after it's been continuously true for `windowSeconds`. We track when
|
|
146
|
+
* the condition first became true (`firstBelowAt`); the rule can only
|
|
147
|
+
* fire once `now - firstBelowAt >= windowSeconds * 1000`.
|
|
148
|
+
*/
|
|
149
|
+
evaluateEfficiencyBelowRule(rule, snapshot, now) {
|
|
150
|
+
const value = snapshot.efficiency.score;
|
|
151
|
+
if (value === null)
|
|
152
|
+
return [];
|
|
153
|
+
const conditionTrue = compareOp(value, rule.threshold, rule.operator);
|
|
154
|
+
const state = this.getOrInitState(rule.id);
|
|
155
|
+
if (!conditionTrue) {
|
|
156
|
+
state.firstBelowAt = undefined;
|
|
157
|
+
return this.applyThresholdState(rule, value, false, now);
|
|
158
|
+
}
|
|
159
|
+
if (state.firstBelowAt === undefined) {
|
|
160
|
+
state.firstBelowAt = now;
|
|
161
|
+
}
|
|
162
|
+
const sustained = now - state.firstBelowAt >= rule.windowSeconds * 1000;
|
|
163
|
+
return this.applyThresholdState(rule, value, sustained, now);
|
|
164
|
+
}
|
|
165
|
+
applyThresholdState(rule, value, triggered, now) {
|
|
166
|
+
const out = [];
|
|
167
|
+
const state = this.getOrInitState(rule.id);
|
|
168
|
+
if (triggered) {
|
|
169
|
+
if (state.status === 'firing')
|
|
170
|
+
return out;
|
|
171
|
+
// idle → firing, but only if outside the post-clear dedupe window.
|
|
172
|
+
const dedupMs = rule.deduplicateSeconds * 1000;
|
|
173
|
+
if (state.lastClearedAt > 0 && now - state.lastClearedAt < dedupMs) {
|
|
174
|
+
// Suppress fire and keep state at idle so the next evaluation
|
|
175
|
+
// past the window can still fire.
|
|
176
|
+
return out;
|
|
177
|
+
}
|
|
178
|
+
state.status = 'firing';
|
|
179
|
+
state.lastFiredAt = now;
|
|
180
|
+
out.push({
|
|
181
|
+
id: rule.id,
|
|
182
|
+
state: 'firing',
|
|
183
|
+
severity: rule.severity,
|
|
184
|
+
title: rule.name,
|
|
185
|
+
description: rule.description ?? defaultDescription(rule, value),
|
|
186
|
+
value,
|
|
187
|
+
threshold: rule.threshold,
|
|
188
|
+
firedAt: now,
|
|
189
|
+
});
|
|
190
|
+
}
|
|
191
|
+
else if (state.status === 'firing') {
|
|
192
|
+
// firing → idle.
|
|
193
|
+
state.status = 'idle';
|
|
194
|
+
const lastFiredAt = state.lastFiredAt;
|
|
195
|
+
state.lastClearedAt = now;
|
|
196
|
+
out.push({
|
|
197
|
+
id: rule.id,
|
|
198
|
+
state: 'cleared',
|
|
199
|
+
severity: rule.severity,
|
|
200
|
+
title: rule.name,
|
|
201
|
+
description: rule.description ?? defaultDescription(rule, value),
|
|
202
|
+
value,
|
|
203
|
+
threshold: rule.threshold,
|
|
204
|
+
firedAt: lastFiredAt,
|
|
205
|
+
});
|
|
206
|
+
}
|
|
207
|
+
return out;
|
|
208
|
+
}
|
|
209
|
+
// ---------------------------------------------------------------------------
|
|
210
|
+
// Per-rule value extractors
|
|
211
|
+
// ---------------------------------------------------------------------------
|
|
212
|
+
/**
|
|
213
|
+
* Cost windows are session/today/week cumulative — not a true rolling
|
|
214
|
+
* window. The engine reads whichever bucket the rule names; a real
|
|
215
|
+
* rolling-N-second cost calculation is not yet implemented.
|
|
216
|
+
*/
|
|
217
|
+
computeCostWindowValue(rule, snapshot) {
|
|
218
|
+
switch (rule.costPeriod) {
|
|
219
|
+
case 'session':
|
|
220
|
+
return snapshot.cost.sessionUsd;
|
|
221
|
+
case 'today':
|
|
222
|
+
return snapshot.cost.todayUsd;
|
|
223
|
+
case 'week':
|
|
224
|
+
return snapshot.cost.weekUsd;
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
computeAntiPatternCountValue(rule, snapshot) {
|
|
228
|
+
const windowMs = rule.windowSeconds * 1000;
|
|
229
|
+
const wantedKey = rule.patternType ?? '*';
|
|
230
|
+
let total = 0;
|
|
231
|
+
let matched = false;
|
|
232
|
+
for (const entry of snapshot.antiPatterns) {
|
|
233
|
+
if (entry.windowMs !== windowMs)
|
|
234
|
+
continue;
|
|
235
|
+
if (entry.type !== wantedKey)
|
|
236
|
+
continue;
|
|
237
|
+
total += entry.count;
|
|
238
|
+
matched = true;
|
|
239
|
+
}
|
|
240
|
+
return matched ? total : null;
|
|
241
|
+
}
|
|
242
|
+
computeLatencyValue(rule, snapshot) {
|
|
243
|
+
if (snapshot.latency.length === 0)
|
|
244
|
+
return null;
|
|
245
|
+
const pickPercentile = (entry) => {
|
|
246
|
+
switch (rule.percentile) {
|
|
247
|
+
case 50:
|
|
248
|
+
return entry.p50Ms;
|
|
249
|
+
case 95:
|
|
250
|
+
return entry.p95Ms;
|
|
251
|
+
case 99:
|
|
252
|
+
return entry.p99Ms;
|
|
253
|
+
}
|
|
254
|
+
};
|
|
255
|
+
if (rule.tool) {
|
|
256
|
+
const entry = snapshot.latency.find((l) => l.tool === rule.tool);
|
|
257
|
+
return entry ? pickPercentile(entry) : null;
|
|
258
|
+
}
|
|
259
|
+
// No tool filter → take the worst (max) value at the requested percentile
|
|
260
|
+
// across all observed tools.
|
|
261
|
+
let max = -Infinity;
|
|
262
|
+
for (const entry of snapshot.latency) {
|
|
263
|
+
const v = pickPercentile(entry);
|
|
264
|
+
if (v > max)
|
|
265
|
+
max = v;
|
|
266
|
+
}
|
|
267
|
+
return max === -Infinity ? null : max;
|
|
268
|
+
}
|
|
269
|
+
computeToolFailureValue(rule, snapshot) {
|
|
270
|
+
const windowMs = rule.windowSeconds * 1000;
|
|
271
|
+
const entry = snapshot.toolFailures.find((f) => f.tool === rule.tool && f.windowMs === windowMs);
|
|
272
|
+
return entry ? entry.failurePct : null;
|
|
273
|
+
}
|
|
274
|
+
evaluateBudgetRule(rule, snapshot, now) {
|
|
275
|
+
const out = [];
|
|
276
|
+
const period = budgetPeriodForRule(rule);
|
|
277
|
+
const thresholds = snapshot.budgetThresholds ?? [];
|
|
278
|
+
// Find the HIGHEST matching threshold so escalation from 50% → 80% produces
|
|
279
|
+
// a new periodKey and fires again rather than being blocked by the 50% key.
|
|
280
|
+
const matching = thresholds
|
|
281
|
+
.filter((t) => t.period === period && t.thresholdPct >= rule.threshold)
|
|
282
|
+
.reduce((best, t) => best === null || t.thresholdPct > best.thresholdPct ? t : best, null);
|
|
283
|
+
const state = this.getOrInitState(rule.id);
|
|
284
|
+
if (matching) {
|
|
285
|
+
// Edge-trigger: build a per-period key so the same threshold doesn't
|
|
286
|
+
// fire twice in the same period unless deduplicateSeconds has elapsed
|
|
287
|
+
// and a higher threshold crossed (BudgetTracker dedupes within a
|
|
288
|
+
// period; this guards against duplicate calls into evaluate()).
|
|
289
|
+
const periodKey = `${matching.period}|${matching.thresholdPct}|${this.periodKey(matching.period, now)}`;
|
|
290
|
+
if (state.firedPeriodKey === periodKey) {
|
|
291
|
+
return out;
|
|
292
|
+
}
|
|
293
|
+
if (state.status === 'firing' &&
|
|
294
|
+
state.firedPeriodKey &&
|
|
295
|
+
now - state.lastFiredAt < rule.deduplicateSeconds * 1000) {
|
|
296
|
+
return out;
|
|
297
|
+
}
|
|
298
|
+
state.status = 'firing';
|
|
299
|
+
state.lastFiredAt = now;
|
|
300
|
+
state.firedPeriodKey = periodKey;
|
|
301
|
+
state.firedSpentUsd = matching.spentUsd;
|
|
302
|
+
out.push({
|
|
303
|
+
id: rule.id,
|
|
304
|
+
state: 'firing',
|
|
305
|
+
severity: rule.severity,
|
|
306
|
+
title: rule.name,
|
|
307
|
+
description: rule.description ??
|
|
308
|
+
`Budget threshold ${matching.thresholdPct}% reached for ${matching.period}`,
|
|
309
|
+
value: matching.thresholdPct,
|
|
310
|
+
threshold: rule.threshold,
|
|
311
|
+
firedAt: now,
|
|
312
|
+
});
|
|
313
|
+
}
|
|
314
|
+
else if (state.status === 'firing') {
|
|
315
|
+
// No matching threshold this cycle. Budget rules clear when the period
|
|
316
|
+
// turns over — i.e. when the periodKey portion of firedPeriodKey no
|
|
317
|
+
// longer matches the current period. Until then, keep the rule firing
|
|
318
|
+
// (no clear event yet). This avoids flapping when BudgetTracker stops
|
|
319
|
+
// re-emitting after the initial fire within a period.
|
|
320
|
+
const stored = state.firedPeriodKey;
|
|
321
|
+
if (stored) {
|
|
322
|
+
const [, , storedPeriodKey] = stored.split('|');
|
|
323
|
+
const currentPeriodKey = this.periodKey(period, now);
|
|
324
|
+
// Session period rolls over via CostTracker reset (new Claude Code
|
|
325
|
+
// session) rather than calendar turnover, so periodKey() returns the
|
|
326
|
+
// constant `'session:infinite'` and storedPeriodKey === currentPeriodKey
|
|
327
|
+
// forever. Detect the reset by watching for sessionUsd dropping below
|
|
328
|
+
// the spent value at fire time.
|
|
329
|
+
const sessionReset = period === 'session' &&
|
|
330
|
+
state.firedSpentUsd !== undefined &&
|
|
331
|
+
snapshot.cost.sessionUsd < state.firedSpentUsd;
|
|
332
|
+
if (storedPeriodKey !== currentPeriodKey || sessionReset) {
|
|
333
|
+
state.status = 'idle';
|
|
334
|
+
const lastFiredAt = state.lastFiredAt;
|
|
335
|
+
// Do not update lastFiredAt here — it must reflect the fire time so
|
|
336
|
+
// that the deduplicateSeconds window for the new period is measured
|
|
337
|
+
// from when the rule last fired, not when it cleared.
|
|
338
|
+
state.firedPeriodKey = undefined;
|
|
339
|
+
state.firedSpentUsd = undefined;
|
|
340
|
+
out.push({
|
|
341
|
+
id: rule.id,
|
|
342
|
+
state: 'cleared',
|
|
343
|
+
severity: rule.severity,
|
|
344
|
+
title: rule.name,
|
|
345
|
+
description: rule.description ?? `Budget rule cleared for ${period}`,
|
|
346
|
+
value: 0,
|
|
347
|
+
threshold: rule.threshold,
|
|
348
|
+
firedAt: lastFiredAt,
|
|
349
|
+
});
|
|
350
|
+
}
|
|
351
|
+
}
|
|
352
|
+
}
|
|
353
|
+
return out;
|
|
354
|
+
}
|
|
355
|
+
getOrInitState(ruleId) {
|
|
356
|
+
let state = this.state.get(ruleId);
|
|
357
|
+
if (!state) {
|
|
358
|
+
state = { status: 'idle', lastFiredAt: 0, lastClearedAt: 0 };
|
|
359
|
+
this.state.set(ruleId, state);
|
|
360
|
+
}
|
|
361
|
+
return state;
|
|
362
|
+
}
|
|
363
|
+
periodKey(period, now) {
|
|
364
|
+
const d = new Date(now);
|
|
365
|
+
if (period === 'session')
|
|
366
|
+
return 'session:infinite';
|
|
367
|
+
if (period === 'daily') {
|
|
368
|
+
const y = d.getFullYear();
|
|
369
|
+
const m = String(d.getMonth() + 1).padStart(2, '0');
|
|
370
|
+
const day = String(d.getDate()).padStart(2, '0');
|
|
371
|
+
return `${y}-${m}-${day}`;
|
|
372
|
+
}
|
|
373
|
+
// ISO 8601 week — mirrors BudgetTracker.currentPeriodId() exactly so
|
|
374
|
+
// period keys match when comparing alert engine state to budget thresholds.
|
|
375
|
+
const utc = new Date(Date.UTC(d.getFullYear(), d.getMonth(), d.getDate()));
|
|
376
|
+
const dayOfWeek = utc.getUTCDay() || 7; // 1=Mon … 7=Sun
|
|
377
|
+
utc.setUTCDate(utc.getUTCDate() + 4 - dayOfWeek); // nearest Thursday
|
|
378
|
+
const yearStart = new Date(Date.UTC(utc.getUTCFullYear(), 0, 1));
|
|
379
|
+
const week = Math.ceil(((utc.getTime() - yearStart.getTime()) / 86_400_000 + 1) / 7);
|
|
380
|
+
const isoYear = utc.getUTCFullYear();
|
|
381
|
+
const weekNum = String(week).padStart(2, '0');
|
|
382
|
+
return `${isoYear}-W${weekNum}`;
|
|
383
|
+
}
|
|
384
|
+
// For tests + Phase 2 hand-off: read-only view of currently firing rules.
|
|
385
|
+
getFiringRuleIds() {
|
|
386
|
+
const ids = [];
|
|
387
|
+
for (const [id, st] of this.state.entries()) {
|
|
388
|
+
if (st.status === 'firing')
|
|
389
|
+
ids.push(id);
|
|
390
|
+
}
|
|
391
|
+
return ids;
|
|
392
|
+
}
|
|
393
|
+
/**
|
|
394
|
+
* Inspect the loaded rule set and return the windows the snapshot
|
|
395
|
+
* collector needs to populate. Each entry is one (kind, key, windowMs)
|
|
396
|
+
* the engine will look for in `evaluate()`. Duplicates are de-duplicated.
|
|
397
|
+
*/
|
|
398
|
+
getRequiredWindows() {
|
|
399
|
+
const seen = new Set();
|
|
400
|
+
const out = [];
|
|
401
|
+
for (const rule of this.rules) {
|
|
402
|
+
if (!rule.enabled)
|
|
403
|
+
continue;
|
|
404
|
+
if (rule.type === 'antipattern.count') {
|
|
405
|
+
const key = rule.patternType ?? '*';
|
|
406
|
+
const windowMs = rule.windowSeconds * 1000;
|
|
407
|
+
const seenKey = `antipattern:${key}:${windowMs}`;
|
|
408
|
+
if (!seen.has(seenKey)) {
|
|
409
|
+
seen.add(seenKey);
|
|
410
|
+
out.push({ kind: 'antipattern', key, windowMs });
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
else if (rule.type === 'tool.failure') {
|
|
414
|
+
const windowMs = rule.windowSeconds * 1000;
|
|
415
|
+
const seenKey = `tool-failure:${rule.tool}:${windowMs}`;
|
|
416
|
+
if (!seen.has(seenKey)) {
|
|
417
|
+
seen.add(seenKey);
|
|
418
|
+
out.push({ kind: 'tool-failure', key: rule.tool, windowMs });
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
}
|
|
422
|
+
return out;
|
|
423
|
+
}
|
|
424
|
+
/** Exposed for Phase 2 wiring; returns the current monotonic clock reading. */
|
|
425
|
+
now() {
|
|
426
|
+
return this.clock();
|
|
427
|
+
}
|
|
428
|
+
}
|
|
429
|
+
// ---------------------------------------------------------------------------
|
|
430
|
+
// Description helpers
|
|
431
|
+
// ---------------------------------------------------------------------------
|
|
432
|
+
function defaultDescription(rule, value) {
|
|
433
|
+
switch (rule.type) {
|
|
434
|
+
case 'cost.window':
|
|
435
|
+
return `Cost ${rule.costPeriod} ${formatOp(rule.operator)} $${rule.threshold} (current: $${value.toFixed(2)})`;
|
|
436
|
+
case 'efficiency.below':
|
|
437
|
+
return `Efficiency score ${formatOp(rule.operator)} ${rule.threshold} (current: ${value})`;
|
|
438
|
+
case 'antipattern.count': {
|
|
439
|
+
const target = rule.patternType ?? 'any';
|
|
440
|
+
return `Anti-pattern (${target}) count ${formatOp(rule.operator)} ${rule.threshold} (current: ${value})`;
|
|
441
|
+
}
|
|
442
|
+
case 'latency.percentile': {
|
|
443
|
+
const target = rule.tool ?? 'any tool';
|
|
444
|
+
return `p${rule.percentile} latency for ${target} ${formatOp(rule.operator)} ${rule.threshold}ms (current: ${value}ms)`;
|
|
445
|
+
}
|
|
446
|
+
case 'tool.failure':
|
|
447
|
+
return `Failure rate for ${rule.tool} ${formatOp(rule.operator)} ${rule.threshold}% (current: ${value.toFixed(1)}%)`;
|
|
448
|
+
case 'budget.session':
|
|
449
|
+
case 'budget.daily':
|
|
450
|
+
case 'budget.weekly':
|
|
451
|
+
return `Budget threshold reached`;
|
|
452
|
+
}
|
|
453
|
+
}
|
|
454
|
+
function formatOp(op) {
|
|
455
|
+
switch (op) {
|
|
456
|
+
case 'above':
|
|
457
|
+
return '>';
|
|
458
|
+
case 'below':
|
|
459
|
+
return '<';
|
|
460
|
+
case 'above_or_equals':
|
|
461
|
+
return '>=';
|
|
462
|
+
case 'below_or_equals':
|
|
463
|
+
return '<=';
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
//# sourceMappingURL=local-alert-engine.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"local-alert-engine.js","sourceRoot":"","sources":["../../src/alerts/local-alert-engine.ts"],"names":[],"mappings":"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"}
|