pi-harness-runtime 1.1.397 → 1.1.402
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/AGENTS.md +44 -2
- package/CHANGELOG.md +21 -0
- package/RULES.md +28 -0
- package/harness/agent-handoff.ts +2 -3
- package/harness/autonomous-review.ts +1 -1
- package/harness/blackboard.ts +2 -3
- package/harness/context-compact-orchestrator.ts +1 -1
- package/harness/context-window-manager.ts +2 -2
- package/harness/e2e/playwright-runner.ts +6 -4
- package/harness/herdr-agents.ts +1 -1
- package/harness/job-state-machine.ts +1 -1
- package/harness/langchain/daemon.ts +3 -3
- package/harness/langchain/graph.ts +2 -2
- package/harness/langchain/ping-pong-middleware.ts +2 -2
- package/harness/loop-code-agent.ts +6 -4
- package/harness/loop-controller.ts +1 -1
- package/harness/loop-review-agent.ts +1 -1
- package/harness/loop-types.ts +1 -1
- package/harness/master-planner.ts +1 -1
- package/harness/notification-events.ts +6 -6
- package/harness/project-detector/detector.ts +1 -2
- package/harness/repair-engine.ts +2 -4
- package/harness/service-diagnostics.ts +1 -1
- package/harness/skill-sync.ts +3 -3
- package/index.ts +276 -55
- package/mirror.ts +1 -1
- package/package.json +5 -3
- package/packages/a2a-adapter/dist/discovery.d.ts.map +1 -1
- package/packages/a2a-adapter/dist/discovery.js +0 -1
- package/packages/a2a-adapter/dist/discovery.js.map +1 -1
- package/packages/a2a-adapter/package.json +1 -1
- package/packages/a2a-adapter/src/discovery.ts +0 -1
- package/packages/agent-policy/package.json +1 -1
- package/packages/architecture-generator/package.json +1 -1
- package/packages/auth/dist/index.d.ts +9 -0
- package/packages/auth/dist/index.d.ts.map +1 -0
- package/packages/auth/dist/index.js +9 -0
- package/packages/auth/dist/index.js.map +1 -0
- package/packages/auth/package.json +1 -1
- package/packages/auth/src/index.ts +9 -0
- package/packages/autonomous-refactor/package.json +1 -1
- package/packages/autonomous-runtime/package.json +1 -1
- package/packages/cache-strategy/package.json +1 -1
- package/packages/capability-registry/package.json +1 -1
- package/packages/checkpoint/package.json +1 -1
- package/packages/cli-plugin-sdk/package.json +1 -1
- package/packages/clipboard/package.json +1 -1
- package/packages/clipboard-plugin/package.json +1 -1
- package/packages/code-generation/package.json +1 -1
- package/packages/code-review/package.json +1 -1
- package/packages/codex-adapter/package.json +1 -1
- package/packages/codex-watcher/package.json +1 -1
- package/packages/config-capture/dist/index.d.ts +52 -0
- package/packages/config-capture/dist/index.d.ts.map +1 -0
- package/packages/config-capture/dist/index.js +261 -0
- package/packages/config-capture/dist/index.js.map +1 -0
- package/packages/config-capture/package.json +1 -1
- package/packages/connection-runtime/package.json +1 -1
- package/packages/context-compiler/package.json +1 -1
- package/packages/context-discovery/package.json +1 -1
- package/packages/context-manager/package.json +1 -1
- package/packages/contracts/package.json +1 -1
- package/packages/cookie-sanitizer/package.json +1 -1
- package/packages/cost-optimizer/package.json +1 -1
- package/packages/dependency-analyzer/package.json +1 -1
- package/packages/django-plugin/package.json +1 -1
- package/packages/doc-generator/package.json +1 -1
- package/packages/durable-review/package.json +1 -1
- package/packages/e2e-tester/package.json +1 -1
- package/packages/evaluation-engine/package.json +1 -1
- package/packages/evaluation-runner/package.json +1 -1
- package/packages/event-bus/package.json +1 -1
- package/packages/event-sink/package.json +1 -1
- package/packages/event-store/package.json +1 -1
- package/packages/experience-replay/package.json +1 -1
- package/packages/feedback-collector/package.json +1 -1
- package/packages/file-copy-helper/dist/extension.d.ts +15 -0
- package/packages/file-copy-helper/dist/extension.d.ts.map +1 -0
- package/packages/file-copy-helper/dist/extension.debug.d.ts +15 -0
- package/packages/file-copy-helper/dist/extension.debug.d.ts.map +1 -0
- package/packages/file-copy-helper/dist/extension.debug.js +215 -0
- package/packages/file-copy-helper/dist/extension.debug.js.map +1 -0
- package/packages/file-copy-helper/dist/extension.js +222 -0
- package/packages/file-copy-helper/dist/extension.js.map +1 -0
- package/packages/file-copy-helper/dist/index.d.ts +3 -0
- package/packages/file-copy-helper/dist/index.d.ts.map +1 -0
- package/packages/file-copy-helper/dist/index.js +3 -0
- package/packages/file-copy-helper/dist/index.js.map +1 -0
- package/packages/file-copy-helper/dist/intent-detector.d.ts +21 -0
- package/packages/file-copy-helper/dist/intent-detector.d.ts.map +1 -0
- package/packages/file-copy-helper/dist/intent-detector.js +348 -0
- package/packages/file-copy-helper/dist/intent-detector.js.map +1 -0
- package/packages/file-copy-helper/package.json +1 -1
- package/packages/framework-detector/package.json +1 -1
- package/packages/framework-plugin-sdk/package.json +1 -1
- package/packages/frappe-plugin/package.json +1 -1
- package/packages/generic-web-plugin/package.json +1 -1
- package/packages/health-monitor/package.json +1 -1
- package/packages/intent-analyzer/package.json +1 -1
- package/packages/jev-judge/dist/auto-continue.d.ts +161 -2
- package/packages/jev-judge/dist/auto-continue.d.ts.map +1 -1
- package/packages/jev-judge/dist/auto-continue.js +267 -22
- package/packages/jev-judge/dist/auto-continue.js.map +1 -1
- package/packages/jev-judge/dist/index.d.ts +2 -0
- package/packages/jev-judge/dist/index.d.ts.map +1 -1
- package/packages/jev-judge/dist/index.js +2 -0
- package/packages/jev-judge/dist/index.js.map +1 -1
- package/packages/jev-judge/dist/question-risk.d.ts +50 -0
- package/packages/jev-judge/dist/question-risk.d.ts.map +1 -0
- package/packages/jev-judge/dist/question-risk.js +100 -0
- package/packages/jev-judge/dist/question-risk.js.map +1 -0
- package/packages/jev-judge/package.json +1 -1
- package/packages/jev-judge/src/auto-continue.ts +426 -29
- package/packages/jev-judge/src/index.ts +4 -0
- package/packages/jev-judge/src/question-risk.ts +151 -0
- package/packages/jev-judge/tests/auto-continue-context.test.ts +221 -0
- package/packages/jev-judge/tests/outcome-application.test.ts +132 -0
- package/packages/jev-judge/tests/question-risk.test.ts +116 -0
- package/packages/knowledge-graph/package.json +1 -1
- package/packages/knowledge-retrieval/package.json +1 -1
- package/packages/laravel-plugin/package.json +1 -1
- package/packages/learning-engine/package.json +1 -1
- package/packages/logging/README.md +36 -3
- package/packages/logging/dist/config.d.ts +7 -0
- package/packages/logging/dist/config.d.ts.map +1 -1
- package/packages/logging/dist/config.js +14 -0
- package/packages/logging/dist/config.js.map +1 -1
- package/packages/logging/dist/incidents/schema.d.ts +111 -0
- package/packages/logging/dist/incidents/schema.d.ts.map +1 -0
- package/packages/logging/dist/incidents/schema.js +0 -0
- package/packages/logging/dist/incidents/schema.js.map +1 -0
- package/packages/logging/dist/index.d.ts +2 -0
- package/packages/logging/dist/index.d.ts.map +1 -1
- package/packages/logging/dist/index.js +2 -0
- package/packages/logging/dist/index.js.map +1 -1
- package/packages/logging/dist/server/http.d.ts +4 -3
- package/packages/logging/dist/server/http.d.ts.map +1 -1
- package/packages/logging/dist/server/http.js +35 -3
- package/packages/logging/dist/server/http.js.map +1 -1
- package/packages/logging/dist/server/incident-qdrant.d.ts +83 -0
- package/packages/logging/dist/server/incident-qdrant.d.ts.map +1 -0
- package/packages/logging/dist/server/incident-qdrant.js +129 -0
- package/packages/logging/dist/server/incident-qdrant.js.map +1 -0
- package/packages/logging/dist/server/incident-store.d.ts +76 -0
- package/packages/logging/dist/server/incident-store.d.ts.map +1 -0
- package/packages/logging/dist/server/incident-store.js +157 -0
- package/packages/logging/dist/server/incident-store.js.map +1 -0
- package/packages/logging/dist/server/index.d.ts +4 -0
- package/packages/logging/dist/server/index.d.ts.map +1 -1
- package/packages/logging/dist/server/index.js +2 -0
- package/packages/logging/dist/server/index.js.map +1 -1
- package/packages/logging/dist/server/service.d.ts +33 -0
- package/packages/logging/dist/server/service.d.ts.map +1 -1
- package/packages/logging/dist/server/service.js +63 -0
- package/packages/logging/dist/server/service.js.map +1 -1
- package/packages/logging/dist/shipper.d.ts +74 -3
- package/packages/logging/dist/shipper.d.ts.map +1 -1
- package/packages/logging/dist/shipper.js +88 -5
- package/packages/logging/dist/shipper.js.map +1 -1
- package/packages/logging/dist/singleton.d.ts.map +1 -1
- package/packages/logging/dist/singleton.js +1 -0
- package/packages/logging/dist/singleton.js.map +1 -1
- package/packages/logging/package.json +1 -1
- package/packages/logging/src/config.ts +22 -0
- package/packages/logging/src/incidents/schema.ts +0 -0
- package/packages/logging/src/index.ts +17 -0
- package/packages/logging/src/server/http.ts +42 -3
- package/packages/logging/src/server/incident-qdrant.ts +177 -0
- package/packages/logging/src/server/incident-store.ts +192 -0
- package/packages/logging/src/server/index.ts +21 -0
- package/packages/logging/src/server/service.ts +79 -0
- package/packages/logging/src/shipper.ts +120 -5
- package/packages/logging/src/singleton.ts +1 -0
- package/packages/logging/test/fanout.test.ts +186 -0
- package/packages/logging/test/incidents.test.ts +404 -0
- package/packages/mcp-adapter/package.json +1 -1
- package/packages/memory-engine/package.json +1 -1
- package/packages/milestone-manager/package.json +1 -1
- package/packages/model-registry/package.json +1 -1
- package/packages/nextjs-plugin/package.json +1 -1
- package/packages/notification/dist/adapters/detail-format.d.ts +42 -0
- package/packages/notification/dist/adapters/detail-format.d.ts.map +1 -0
- package/packages/notification/dist/adapters/detail-format.js +94 -0
- package/packages/notification/dist/adapters/detail-format.js.map +1 -0
- package/packages/notification/dist/adapters/email-adapter.d.ts.map +1 -1
- package/packages/notification/dist/adapters/email-adapter.js +3 -2
- package/packages/notification/dist/adapters/email-adapter.js.map +1 -1
- package/packages/notification/dist/adapters/line-adapter.d.ts +33 -0
- package/packages/notification/dist/adapters/line-adapter.d.ts.map +1 -1
- package/packages/notification/dist/adapters/line-adapter.js +87 -9
- package/packages/notification/dist/adapters/line-adapter.js.map +1 -1
- package/packages/notification/dist/adapters/ntfy-adapter.d.ts.map +1 -1
- package/packages/notification/dist/adapters/ntfy-adapter.js +3 -2
- package/packages/notification/dist/adapters/ntfy-adapter.js.map +1 -1
- package/packages/notification/dist/adapters/telegram-adapter.d.ts +14 -0
- package/packages/notification/dist/adapters/telegram-adapter.d.ts.map +1 -1
- package/packages/notification/dist/adapters/telegram-adapter.js +89 -69
- package/packages/notification/dist/adapters/telegram-adapter.js.map +1 -1
- package/packages/notification/dist/notification-center.d.ts.map +1 -1
- package/packages/notification/dist/notification-center.js +60 -7
- package/packages/notification/dist/notification-center.js.map +1 -1
- package/packages/notification/dist/pending-question.d.ts +69 -2
- package/packages/notification/dist/pending-question.d.ts.map +1 -1
- package/packages/notification/dist/pending-question.js +88 -2
- package/packages/notification/dist/pending-question.js.map +1 -1
- package/packages/notification/dist/types.d.ts +21 -0
- package/packages/notification/dist/types.d.ts.map +1 -1
- package/packages/notification/package.json +1 -1
- package/packages/notification/src/adapters/detail-format.ts +114 -0
- package/packages/notification/src/adapters/email-adapter.ts +3 -2
- package/packages/notification/src/adapters/line-adapter.ts +97 -9
- package/packages/notification/src/adapters/ntfy-adapter.ts +3 -2
- package/packages/notification/src/adapters/telegram-adapter.ts +98 -76
- package/packages/notification/src/notification-center.ts +66 -8
- package/packages/notification/src/pending-question.ts +160 -8
- package/packages/notification/src/types.ts +21 -0
- package/packages/notification/test/approval-payload.test.ts +269 -0
- package/packages/notification/test/detail-format.test.ts +106 -0
- package/packages/notification/test/pending-question-lifecycle.test.ts +195 -0
- package/packages/observability/package.json +1 -1
- package/packages/okf-indexer/dist/index.d.ts +9 -0
- package/packages/okf-indexer/dist/index.d.ts.map +1 -0
- package/packages/okf-indexer/dist/index.js +9 -0
- package/packages/okf-indexer/dist/index.js.map +1 -0
- package/packages/okf-indexer/package.json +1 -1
- package/packages/okf-indexer/src/index.ts +9 -0
- package/packages/paperclip-integration/package.json +1 -1
- package/packages/performance-optimizer/package.json +1 -1
- package/packages/permission-mode/package.json +1 -1
- package/packages/privilege-broker/package.json +1 -1
- package/packages/project-analyzer/package.json +1 -1
- package/packages/project-bootstrap/package.json +1 -1
- package/packages/projection-engine/package.json +1 -1
- package/packages/prompt-compiler/package.json +1 -1
- package/packages/prompt-versioning/package.json +1 -1
- package/packages/provider-adapter-sdk/package.json +1 -1
- package/packages/provider-router/dist/provider-router.d.ts.map +1 -1
- package/packages/provider-router/dist/types.d.ts +2 -2
- package/packages/provider-router/dist/types.d.ts.map +1 -1
- package/packages/provider-router/dist/types.js +1 -1
- package/packages/provider-router/package.json +1 -1
- package/packages/provider-router/src/types.ts +2 -2
- package/packages/provider-selector/package.json +1 -1
- package/packages/providers/package.json +1 -1
- package/packages/qdrant-skills/package.json +1 -1
- package/packages/quota-manager/package.json +1 -1
- package/packages/rate-limiter/package.json +1 -1
- package/packages/react-vite-plugin/package.json +1 -1
- package/packages/relay/package.json +1 -1
- package/packages/release-manager/package.json +1 -1
- package/packages/requirement-compiler/package.json +1 -1
- package/packages/runtime/package.json +1 -1
- package/packages/scheduler/dist/index.d.ts +9 -0
- package/packages/scheduler/dist/index.d.ts.map +1 -0
- package/packages/scheduler/dist/index.js +9 -0
- package/packages/scheduler/dist/index.js.map +1 -0
- package/packages/scheduler/dist/scheduler.d.ts +17 -0
- package/packages/scheduler/dist/scheduler.d.ts.map +1 -0
- package/packages/scheduler/dist/scheduler.js +41 -0
- package/packages/scheduler/dist/scheduler.js.map +1 -0
- package/packages/scheduler/package.json +1 -1
- package/packages/scheduler/src/index.ts +9 -0
- package/packages/scheduler-adapter/package.json +1 -1
- package/packages/session/package.json +1 -1
- package/packages/session-api/package.json +1 -1
- package/packages/session-export/package.json +1 -1
- package/packages/shared-context/dist/index.d.ts +7 -0
- package/packages/shared-context/dist/index.d.ts.map +1 -0
- package/packages/shared-context/dist/index.js +7 -0
- package/packages/shared-context/dist/index.js.map +1 -0
- package/packages/shared-context/dist/shared-context.d.ts +12 -0
- package/packages/shared-context/dist/shared-context.d.ts.map +1 -0
- package/packages/shared-context/dist/shared-context.js +39 -0
- package/packages/shared-context/dist/shared-context.js.map +1 -0
- package/packages/shared-context/package.json +1 -1
- package/packages/skill-mcp-client/dist/client.d.ts +56 -0
- package/packages/skill-mcp-client/dist/client.d.ts.map +1 -0
- package/packages/skill-mcp-client/dist/client.js +101 -0
- package/packages/skill-mcp-client/dist/client.js.map +1 -0
- package/packages/skill-mcp-client/dist/errors.d.ts +44 -0
- package/packages/skill-mcp-client/dist/errors.d.ts.map +1 -0
- package/packages/skill-mcp-client/dist/errors.js +68 -0
- package/packages/skill-mcp-client/dist/errors.js.map +1 -0
- package/packages/skill-mcp-client/dist/index.d.ts +9 -0
- package/packages/skill-mcp-client/dist/index.d.ts.map +1 -0
- package/packages/skill-mcp-client/dist/index.js +9 -0
- package/packages/skill-mcp-client/dist/index.js.map +1 -0
- package/packages/skill-mcp-client/dist/types.d.ts +106 -0
- package/packages/skill-mcp-client/dist/types.d.ts.map +1 -0
- package/packages/skill-mcp-client/dist/types.js +14 -0
- package/packages/skill-mcp-client/dist/types.js.map +1 -0
- package/packages/skill-mcp-client/package.json +1 -1
- package/packages/skill-registry/package.json +1 -1
- package/packages/skills/package.json +1 -5
- package/packages/sprint-planner/package.json +1 -1
- package/packages/subscription-engine/package.json +1 -1
- package/packages/task-compiler/package.json +1 -1
- package/packages/telegram/package.json +1 -1
- package/packages/telegram/src/agent-messages.d.ts +28 -0
- package/packages/telegram/src/agent-messages.js +90 -0
- package/packages/telegram/src/bindings.d.ts +296 -0
- package/packages/telegram/src/bindings.js +1086 -0
- package/packages/telegram/src/bus.d.ts +759 -0
- package/packages/telegram/src/bus.js +2732 -0
- package/packages/telegram/src/commands.d.ts +761 -0
- package/packages/telegram/src/commands.js +2622 -0
- package/packages/telegram/src/config.d.ts +222 -0
- package/packages/telegram/src/config.js +844 -0
- package/packages/telegram/src/delivery.d.ts +161 -0
- package/packages/telegram/src/delivery.js +550 -0
- package/packages/telegram/src/extension.d.ts +7 -0
- package/packages/telegram/src/extension.js +2444 -0
- package/packages/telegram/src/inbound.d.ts +94 -0
- package/packages/telegram/src/inbound.js +478 -0
- package/packages/telegram/src/index.d.ts +6 -0
- package/packages/telegram/src/index.js +6 -0
- package/packages/telegram/src/keyboard.d.ts +21 -0
- package/packages/telegram/src/keyboard.js +37 -0
- package/packages/telegram/src/lifecycle.d.ts +210 -0
- package/packages/telegram/src/lifecycle.js +538 -0
- package/packages/telegram/src/pi.d.ts +76 -0
- package/packages/telegram/src/pi.js +130 -0
- package/packages/telegram/src/polling.d.ts +332 -0
- package/packages/telegram/src/polling.js +1219 -0
- package/packages/telegram/src/replies.d.ts +210 -0
- package/packages/telegram/src/replies.js +752 -0
- package/packages/telegram/src/routing.d.ts +388 -0
- package/packages/telegram/src/routing.js +7886 -0
- package/packages/telegram/src/runtime.d.ts +159 -0
- package/packages/telegram/src/runtime.js +351 -0
- package/packages/telegram/src/telegram-api.d.ts +564 -0
- package/packages/telegram/src/telegram-api.js +1332 -0
- package/packages/telegram/src/turns.d.ts +108 -0
- package/packages/telegram/src/turns.js +482 -0
- package/packages/telegram/src/updates.d.ts +1545 -0
- package/packages/telegram/src/updates.js +6420 -0
- package/packages/tencentdb-memory/package.json +1 -1
- package/packages/tencentdb-sync/package.json +1 -1
- package/packages/test-data-generator/package.json +1 -1
- package/packages/test-generator/package.json +1 -1
- package/packages/todo-bd-sync/dist/detector.d.ts +54 -0
- package/packages/todo-bd-sync/dist/detector.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/detector.js +132 -0
- package/packages/todo-bd-sync/dist/detector.js.map +1 -0
- package/packages/todo-bd-sync/dist/extension.d.ts +30 -0
- package/packages/todo-bd-sync/dist/extension.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/extension.js +35 -0
- package/packages/todo-bd-sync/dist/extension.js.map +1 -0
- package/packages/todo-bd-sync/dist/index.d.ts +87 -0
- package/packages/todo-bd-sync/dist/index.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/index.js +296 -0
- package/packages/todo-bd-sync/dist/index.js.map +1 -0
- package/packages/todo-bd-sync/dist/sync.d.ts +72 -0
- package/packages/todo-bd-sync/dist/sync.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/sync.js +290 -0
- package/packages/todo-bd-sync/dist/sync.js.map +1 -0
- package/packages/todo-bd-sync/dist/task-analyzer.d.ts +49 -0
- package/packages/todo-bd-sync/dist/task-analyzer.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/task-analyzer.js +240 -0
- package/packages/todo-bd-sync/dist/task-analyzer.js.map +1 -0
- package/packages/todo-bd-sync/dist/todo-reminder.d.ts +126 -0
- package/packages/todo-bd-sync/dist/todo-reminder.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/todo-reminder.js +329 -0
- package/packages/todo-bd-sync/dist/todo-reminder.js.map +1 -0
- package/packages/todo-bd-sync/dist/types.d.ts +65 -0
- package/packages/todo-bd-sync/dist/types.d.ts.map +1 -0
- package/packages/todo-bd-sync/dist/types.js +67 -0
- package/packages/todo-bd-sync/dist/types.js.map +1 -0
- package/packages/todo-bd-sync/package.json +1 -1
- package/packages/token-estimation/dist/index.d.ts +94 -0
- package/packages/token-estimation/dist/index.d.ts.map +1 -0
- package/packages/token-estimation/dist/index.js +115 -0
- package/packages/token-estimation/dist/index.js.map +1 -0
- package/packages/token-estimation/package.json +1 -1
- package/packages/token-optimizer/package.json +1 -1
- package/packages/trajectory/package.json +1 -1
- package/packages/tui/package.json +1 -1
- package/packages/types/dist/ai-providers.d.ts +36 -0
- package/packages/types/dist/ai-providers.d.ts.map +1 -0
- package/packages/types/dist/ai-providers.js +66 -0
- package/packages/types/dist/ai-providers.js.map +1 -0
- package/packages/types/dist/index.d.ts +12 -0
- package/packages/types/dist/index.d.ts.map +1 -0
- package/packages/types/dist/index.js +12 -0
- package/packages/types/dist/index.js.map +1 -0
- package/packages/types/package.json +5 -5
- package/packages/types/src/index.ts +12 -0
- package/packages/voice-api/package.json +1 -1
- package/packages/webmcp-tester/package.json +1 -1
- package/packages/wiki/package.json +1 -1
- package/packages/workflow-events/package.json +1 -1
- package/packages/workspace-scanner/package.json +1 -1
- package/packages/worktree/package.json +1 -1
- package/packages/worktree/worktree.ts +1 -1
- package/packages/write-review/package.json +1 -1
- package/renderer.ts +1 -1
- package/scripts/build-packages.ts +162 -0
- package/scripts/relay-client.ts +2 -2
- package/scripts/typecheck-packages.mjs +3 -3
- package/scripts/unified-webhook-server.ts +22 -10
- package/scripts/verify-package-contents.ts +345 -0
- package/scripts/ws-server.ts +1 -1
- package/tracker.ts +1 -1
- package/harness/browser-scrapers/base-browser-scraper.d.ts +0 -91
- package/harness/browser-scrapers/chrome-profile-manager.d.ts +0 -80
- package/harness/browser-scrapers/codex-browser-scraper.d.ts +0 -60
- package/harness/browser-scrapers/index.d.ts +0 -29
- package/harness/browser-scrapers/zai-browser-scraper.d.ts +0 -79
- package/harness/e2e/browser-scrapers/base-browser-scraper.d.ts +0 -92
- package/harness/e2e/browser-scrapers/chrome-profile-manager.d.ts +0 -81
- package/harness/e2e/browser-scrapers/codex-browser-scraper.d.ts +0 -61
- package/harness/e2e/browser-scrapers/index.d.ts +0 -30
- package/harness/e2e/browser-scrapers/zai-browser-scraper.d.ts +0 -80
- package/harness/langchain/agents.d.ts +0 -143
- package/harness/langchain/agents.test.d.ts +0 -2
- package/harness/langchain/checkpointer.d.ts +0 -48
- package/harness/langchain/checkpointer.test.d.ts +0 -8
- package/harness/langchain/cron-cli.d.ts +0 -12
- package/harness/langchain/daemon.d.ts +0 -161
- package/harness/langchain/daemon.test.d.ts +0 -11
- package/harness/langchain/file-tools.d.ts +0 -97
- package/harness/langchain/graph.d.ts +0 -706
- package/harness/langchain/model-router.d.ts +0 -63
- package/harness/langchain/model-router.test.d.ts +0 -2
- package/harness/langchain/models.d.ts +0 -72
- package/harness/langchain/ping-pong-middleware.d.ts +0 -28
- package/harness/langchain/ping-pong-middleware.test.d.ts +0 -2
- package/harness/langchain/run.d.ts +0 -15
- package/harness/langchain/scoreboard.test.d.ts +0 -13
- package/harness/langchain/status-line.d.ts +0 -91
- package/harness/langchain/status-line.test.d.ts +0 -8
- package/harness/langchain/surge.d.ts +0 -111
- package/harness/langchain/surge.test.d.ts +0 -10
- package/harness/langchain/widget.d.ts +0 -105
- package/harness/langchain/widget.test.d.ts +0 -8
- package/packages/autonomous-runtime/dist/worker.d.ts +0 -63
- package/packages/autonomous-runtime/dist/worker.js +0 -133
- package/packages/capability-registry/src/types.d.ts +0 -47
- package/packages/clipboard/dist/clipboard.d.ts +0 -11
- package/packages/clipboard/dist/clipboard.js +0 -40
- package/packages/clipboard/dist/index.d.ts +0 -2
- package/packages/clipboard/dist/index.js +0 -2
- package/packages/clipboard/dist/types.d.ts +0 -13
- package/packages/clipboard/dist/types.js +0 -5
- package/packages/context-discovery/dist/discover.d.ts +0 -3
- package/packages/context-discovery/dist/discover.js +0 -42
- package/packages/context-discovery/dist/discovery.d.ts +0 -28
- package/packages/context-discovery/dist/discovery.js +0 -21
- package/packages/context-discovery/dist/index.d.ts +0 -3
- package/packages/context-discovery/dist/index.js +0 -2
- package/packages/context-discovery/dist/types.d.ts +0 -16
- package/packages/context-discovery/dist/types.js +0 -2
- package/packages/event-bus/dist/bus.d.ts +0 -15
- package/packages/event-bus/dist/bus.js +0 -90
- package/packages/event-bus/dist/index.d.ts +0 -4
- package/packages/event-bus/dist/index.js +0 -3
- package/packages/event-bus/dist/test/bus.test.js +0 -52
- package/packages/event-bus/dist/types.d.ts +0 -27
- package/packages/event-bus/dist/types.js +0 -10
- package/packages/event-store/dist/index.d.ts +0 -3
- package/packages/event-store/dist/index.js +0 -2
- package/packages/event-store/dist/store.d.ts +0 -15
- package/packages/event-store/dist/store.js +0 -131
- package/packages/event-store/dist/test/store.test.js +0 -57
- package/packages/event-store/dist/types.d.ts +0 -48
- package/packages/event-store/dist/types.js +0 -5
- package/packages/event-store/src/types.d.ts +0 -48
- package/packages/file-copy-helper/dist/src/extension.js +0 -186
- package/packages/model-registry/src/types.d.ts +0 -63
- package/packages/notification/dist/src/adapters/email-adapter.d.ts +0 -17
- package/packages/notification/dist/src/adapters/email-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/adapters/email-adapter.js +0 -89
- package/packages/notification/dist/src/adapters/email-adapter.js.map +0 -1
- package/packages/notification/dist/src/adapters/line-adapter.d.ts +0 -17
- package/packages/notification/dist/src/adapters/line-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/adapters/line-adapter.js +0 -99
- package/packages/notification/dist/src/adapters/line-adapter.js.map +0 -1
- package/packages/notification/dist/src/adapters/ntfy-adapter.d.ts +0 -17
- package/packages/notification/dist/src/adapters/ntfy-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/adapters/ntfy-adapter.js +0 -84
- package/packages/notification/dist/src/adapters/ntfy-adapter.js.map +0 -1
- package/packages/notification/dist/src/adapters/telegram-adapter.d.ts +0 -56
- package/packages/notification/dist/src/adapters/telegram-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/adapters/telegram-adapter.js +0 -251
- package/packages/notification/dist/src/adapters/telegram-adapter.js.map +0 -1
- package/packages/notification/dist/src/adapters/webhook-adapter.d.ts +0 -15
- package/packages/notification/dist/src/adapters/webhook-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/adapters/webhook-adapter.js +0 -64
- package/packages/notification/dist/src/adapters/webhook-adapter.js.map +0 -1
- package/packages/notification/dist/src/base-adapter.d.ts +0 -36
- package/packages/notification/dist/src/base-adapter.d.ts.map +0 -1
- package/packages/notification/dist/src/base-adapter.js +0 -39
- package/packages/notification/dist/src/base-adapter.js.map +0 -1
- package/packages/notification/dist/src/index.d.ts +0 -12
- package/packages/notification/dist/src/index.d.ts.map +0 -1
- package/packages/notification/dist/src/index.js +0 -12
- package/packages/notification/dist/src/index.js.map +0 -1
- package/packages/notification/dist/src/notification-center.d.ts +0 -89
- package/packages/notification/dist/src/notification-center.d.ts.map +0 -1
- package/packages/notification/dist/src/notification-center.js +0 -356
- package/packages/notification/dist/src/notification-center.js.map +0 -1
- package/packages/notification/dist/src/notification-policy.d.ts +0 -66
- package/packages/notification/dist/src/notification-policy.d.ts.map +0 -1
- package/packages/notification/dist/src/notification-policy.js +0 -153
- package/packages/notification/dist/src/notification-policy.js.map +0 -1
- package/packages/notification/dist/src/telegram-webhook-handler.d.ts +0 -86
- package/packages/notification/dist/src/telegram-webhook-handler.d.ts.map +0 -1
- package/packages/notification/dist/src/telegram-webhook-handler.js +0 -149
- package/packages/notification/dist/src/telegram-webhook-handler.js.map +0 -1
- package/packages/notification/dist/src/types.d.ts +0 -106
- package/packages/notification/dist/src/types.d.ts.map +0 -1
- package/packages/notification/dist/src/types.js +0 -7
- package/packages/notification/dist/src/types.js.map +0 -1
- package/packages/projection-engine/dist/engine.d.ts +0 -61
- package/packages/projection-engine/dist/engine.js +0 -76
- package/packages/projection-engine/dist/index.d.ts +0 -2
- package/packages/projection-engine/dist/index.js +0 -2
- package/packages/projection-engine/dist/project.d.ts +0 -3
- package/packages/projection-engine/dist/project.js +0 -24
- package/packages/projection-engine/dist/types.d.ts +0 -55
- package/packages/projection-engine/dist/types.js +0 -5
- package/packages/projection-engine/src/types.d.ts +0 -55
- package/packages/provider-adapter-sdk/dist/src/builder.d.ts +0 -140
- package/packages/provider-adapter-sdk/dist/src/builder.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/builder.js +0 -332
- package/packages/provider-adapter-sdk/dist/src/builder.js.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/errors.d.ts +0 -71
- package/packages/provider-adapter-sdk/dist/src/errors.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/errors.js +0 -111
- package/packages/provider-adapter-sdk/dist/src/errors.js.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/index.d.ts +0 -15
- package/packages/provider-adapter-sdk/dist/src/index.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/index.js +0 -19
- package/packages/provider-adapter-sdk/dist/src/index.js.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/registry.d.ts +0 -108
- package/packages/provider-adapter-sdk/dist/src/registry.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/registry.js +0 -301
- package/packages/provider-adapter-sdk/dist/src/registry.js.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/tester.d.ts +0 -71
- package/packages/provider-adapter-sdk/dist/src/tester.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/tester.js +0 -392
- package/packages/provider-adapter-sdk/dist/src/tester.js.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/types.d.ts +0 -182
- package/packages/provider-adapter-sdk/dist/src/types.d.ts.map +0 -1
- package/packages/provider-adapter-sdk/dist/src/types.js +0 -11
- package/packages/provider-adapter-sdk/dist/src/types.js.map +0 -1
- package/packages/provider-router/dist/capability-registry/src/types.d.ts +0 -47
- package/packages/provider-router/dist/capability-registry/src/types.d.ts.map +0 -1
- package/packages/provider-router/dist/capability-registry/src/types.js +0 -10
- package/packages/provider-router/dist/capability-registry/src/types.js.map +0 -1
- package/packages/provider-router/dist/provider-router/src/index.d.ts +0 -23
- package/packages/provider-router/dist/provider-router/src/index.d.ts.map +0 -1
- package/packages/provider-router/dist/provider-router/src/index.js +0 -25
- package/packages/provider-router/dist/provider-router/src/index.js.map +0 -1
- package/packages/provider-router/dist/provider-router/src/policy.d.ts +0 -10
- package/packages/provider-router/dist/provider-router/src/policy.d.ts.map +0 -1
- package/packages/provider-router/dist/provider-router/src/policy.js +0 -45
- package/packages/provider-router/dist/provider-router/src/policy.js.map +0 -1
- package/packages/provider-router/dist/provider-router/src/provider-router.d.ts +0 -56
- package/packages/provider-router/dist/provider-router/src/provider-router.d.ts.map +0 -1
- package/packages/provider-router/dist/provider-router/src/provider-router.js +0 -222
- package/packages/provider-router/dist/provider-router/src/provider-router.js.map +0 -1
- package/packages/provider-router/dist/provider-router/src/strategies.d.ts +0 -19
- package/packages/provider-router/dist/provider-router/src/strategies.d.ts.map +0 -1
- package/packages/provider-router/dist/provider-router/src/strategies.js +0 -110
- package/packages/provider-router/dist/provider-router/src/strategies.js.map +0 -1
- package/packages/provider-router/dist/provider-router/src/types.d.ts +0 -91
- package/packages/provider-router/dist/provider-router/src/types.d.ts.map +0 -1
- package/packages/provider-router/dist/provider-router/src/types.js +0 -10
- package/packages/provider-router/dist/provider-router/src/types.js.map +0 -1
- package/packages/provider-router/dist/src/index.d.ts +0 -23
- package/packages/provider-router/dist/src/index.d.ts.map +0 -1
- package/packages/provider-router/dist/src/index.js +0 -25
- package/packages/provider-router/dist/src/index.js.map +0 -1
- package/packages/provider-router/dist/src/policy.d.ts +0 -10
- package/packages/provider-router/dist/src/policy.d.ts.map +0 -1
- package/packages/provider-router/dist/src/policy.js +0 -45
- package/packages/provider-router/dist/src/policy.js.map +0 -1
- package/packages/provider-router/dist/src/provider-router.d.ts +0 -56
- package/packages/provider-router/dist/src/provider-router.d.ts.map +0 -1
- package/packages/provider-router/dist/src/provider-router.js +0 -222
- package/packages/provider-router/dist/src/provider-router.js.map +0 -1
- package/packages/provider-router/dist/src/strategies.d.ts +0 -19
- package/packages/provider-router/dist/src/strategies.d.ts.map +0 -1
- package/packages/provider-router/dist/src/strategies.js +0 -110
- package/packages/provider-router/dist/src/strategies.js.map +0 -1
- package/packages/provider-router/dist/src/types.d.ts +0 -91
- package/packages/provider-router/dist/src/types.d.ts.map +0 -1
- package/packages/provider-router/dist/src/types.js +0 -10
- package/packages/provider-router/dist/src/types.js.map +0 -1
- package/packages/provider-router/dist/types/src/runtime-types.d.ts +0 -412
- package/packages/provider-router/dist/types/src/runtime-types.d.ts.map +0 -1
- package/packages/provider-router/dist/types/src/runtime-types.js +0 -2
- package/packages/provider-router/dist/types/src/runtime-types.js.map +0 -1
- package/packages/session-api/dist/api.d.ts +0 -83
- package/packages/session-api/dist/api.js +0 -35
- package/packages/session-api/dist/index.d.ts +0 -2
- package/packages/session-api/dist/index.js +0 -2
- package/packages/session-api/dist/types.d.ts +0 -22
- package/packages/session-api/dist/types.js +0 -5
- package/packages/session-export/dist/exporter.d.ts +0 -28
- package/packages/session-export/dist/exporter.js +0 -38
- package/packages/session-export/dist/index.d.ts +0 -2
- package/packages/session-export/dist/index.js +0 -2
- package/packages/session-export/dist/types.d.ts +0 -20
- package/packages/session-export/dist/types.js +0 -5
- package/packages/subscription-engine/dist/engine.d.ts +0 -13
- package/packages/subscription-engine/dist/engine.js +0 -40
- package/packages/subscription-engine/dist/index.d.ts +0 -2
- package/packages/subscription-engine/dist/index.js +0 -2
- package/packages/subscription-engine/dist/subscriptions.d.ts +0 -19
- package/packages/subscription-engine/dist/subscriptions.js +0 -32
- package/packages/subscription-engine/dist/types.d.ts +0 -24
- package/packages/subscription-engine/dist/types.js +0 -5
- package/packages/trajectory/test/store.test.d.ts +0 -2
- package/packages/workflow-events/dist/events.d.ts +0 -38
- package/packages/workflow-events/dist/events.js +0 -46
- package/packages/workflow-events/dist/index.d.ts +0 -2
- package/packages/workflow-events/dist/index.js +0 -2
- package/packages/workflow-events/dist/pipeline.d.ts +0 -21
- package/packages/workflow-events/dist/pipeline.js +0 -27
- package/packages/workflow-events/dist/types.d.ts +0 -110
- package/packages/workflow-events/dist/types.js +0 -5
- package/packages/workflow-events/src/types.d.ts +0 -110
|
@@ -0,0 +1,192 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Durable incident storage.
|
|
3
|
+
*
|
|
4
|
+
* The log index answers "which records exist"; the incident store answers
|
|
5
|
+
* "what is actually broken". It keeps the derived incidents of a tenant in
|
|
6
|
+
* plain NDJSON files, one per tenant and day:
|
|
7
|
+
*
|
|
8
|
+
* <dir>/<tenant>/incidents-<day>.ndjson
|
|
9
|
+
*
|
|
10
|
+
* The store is tenant scoped by construction: the tenant is a parameter of
|
|
11
|
+
* every method and the server fills it from the authenticated credential.
|
|
12
|
+
* A caller can therefore never read or write another tenant's incidents.
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
import { appendFileSync, existsSync, mkdirSync, readFileSync, readdirSync } from "node:fs";
|
|
16
|
+
import { join } from "node:path";
|
|
17
|
+
import {
|
|
18
|
+
INCIDENT_SCHEMA_VERSION,
|
|
19
|
+
mergeIncident,
|
|
20
|
+
type LogIncident,
|
|
21
|
+
} from "../incidents/schema.js";
|
|
22
|
+
import { safeSegment } from "./outbox.js";
|
|
23
|
+
|
|
24
|
+
export interface IncidentQueryParams {
|
|
25
|
+
/** Tenant of the authenticated caller. Required. */
|
|
26
|
+
tenantId: string;
|
|
27
|
+
/** Only incidents of this severity. */
|
|
28
|
+
severity?: "warn" | "error";
|
|
29
|
+
/** Only incidents of this component. */
|
|
30
|
+
source?: string;
|
|
31
|
+
/** Only incidents of this event. */
|
|
32
|
+
event?: string;
|
|
33
|
+
/** ISO timestamp, inclusive lower bound on `lastSeen`. */
|
|
34
|
+
since?: string;
|
|
35
|
+
/** ISO timestamp, exclusive upper bound on `lastSeen`. */
|
|
36
|
+
until?: string;
|
|
37
|
+
/** Maximum number of incidents. Default 50, hard maximum 200. */
|
|
38
|
+
limit?: number;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export interface IncidentQueryResult {
|
|
42
|
+
incidents: LogIncident[];
|
|
43
|
+
/** True when the scan hit its day budget. */
|
|
44
|
+
truncated: boolean;
|
|
45
|
+
/** Number of day files that were read. */
|
|
46
|
+
scannedFiles: number;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
export interface IncidentStoreOptions {
|
|
50
|
+
dir: string;
|
|
51
|
+
/** Days a query may scan back. Default 7, hard maximum 31. */
|
|
52
|
+
maxScanDays?: number;
|
|
53
|
+
/** Incidents per page by default. */
|
|
54
|
+
defaultLimit?: number;
|
|
55
|
+
/** Hard maximum of incidents per page. */
|
|
56
|
+
maxLimit?: number;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function toIsoDay(value: Date): string {
|
|
60
|
+
return value.toISOString().slice(0, 10);
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
export class IncidentStore {
|
|
64
|
+
private readonly dir: string;
|
|
65
|
+
private readonly maxScanDays: number;
|
|
66
|
+
private readonly defaultLimit: number;
|
|
67
|
+
private readonly maxLimit: number;
|
|
68
|
+
|
|
69
|
+
constructor(options: IncidentStoreOptions) {
|
|
70
|
+
this.dir = options.dir;
|
|
71
|
+
this.maxScanDays = Math.min(options.maxScanDays ?? 7, 31);
|
|
72
|
+
this.defaultLimit = options.defaultLimit ?? 50;
|
|
73
|
+
this.maxLimit = options.maxLimit ?? 200;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Persist the incidents of one batch.
|
|
78
|
+
*
|
|
79
|
+
* The write is best effort: a failing store must never lose the batch
|
|
80
|
+
* itself. The returned number is the number of incidents that were
|
|
81
|
+
* written.
|
|
82
|
+
*/
|
|
83
|
+
append(incidents: LogIncident[]): number {
|
|
84
|
+
if (!Array.isArray(incidents) || incidents.length === 0) return 0;
|
|
85
|
+
const lines = incidents
|
|
86
|
+
.filter((incident) => incident && incident.fingerprint)
|
|
87
|
+
.map((incident) => JSON.stringify({ ...incident, schemaVersion: INCIDENT_SCHEMA_VERSION }));
|
|
88
|
+
if (lines.length === 0) return 0;
|
|
89
|
+
|
|
90
|
+
const day = toIsoDay(new Date());
|
|
91
|
+
try {
|
|
92
|
+
const dir = join(this.dir, safeSegment(incidents[0].tenantId));
|
|
93
|
+
mkdirSync(dir, { recursive: true });
|
|
94
|
+
appendFileSync(join(dir, `incidents-${day}.ndjson`), `${lines.join("\n")}\n`, {
|
|
95
|
+
mode: 0o600,
|
|
96
|
+
});
|
|
97
|
+
return lines.length;
|
|
98
|
+
} catch {
|
|
99
|
+
return 0;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Query the incidents of one tenant.
|
|
105
|
+
*
|
|
106
|
+
* The incidents of the scanned files are merged by fingerprint, so a
|
|
107
|
+
* failure that was seen in many batches is one incident with a summed
|
|
108
|
+
* count, not many incidents.
|
|
109
|
+
*/
|
|
110
|
+
query(params: IncidentQueryParams): IncidentQueryResult {
|
|
111
|
+
const limit = Math.min(params.limit ?? this.defaultLimit, this.maxLimit);
|
|
112
|
+
const dir = join(this.dir, safeSegment(params.tenantId));
|
|
113
|
+
const merged = new Map<string, LogIncident>();
|
|
114
|
+
let scannedFiles = 0;
|
|
115
|
+
let truncated = false;
|
|
116
|
+
|
|
117
|
+
for (const day of this.dayRange(params.since)) {
|
|
118
|
+
const path = join(dir, `incidents-${day}.ndjson`);
|
|
119
|
+
if (!existsSync(path)) continue;
|
|
120
|
+
scannedFiles++;
|
|
121
|
+
let content: string;
|
|
122
|
+
try {
|
|
123
|
+
content = readFileSync(path, "utf8");
|
|
124
|
+
} catch {
|
|
125
|
+
continue;
|
|
126
|
+
}
|
|
127
|
+
for (const line of content.split("\n")) {
|
|
128
|
+
if (!line.trim()) continue;
|
|
129
|
+
let incident: LogIncident;
|
|
130
|
+
try {
|
|
131
|
+
incident = JSON.parse(line) as LogIncident;
|
|
132
|
+
} catch {
|
|
133
|
+
continue;
|
|
134
|
+
}
|
|
135
|
+
if (!incident.fingerprint) continue;
|
|
136
|
+
if (!this.matches(incident, params)) continue;
|
|
137
|
+
const existing = merged.get(incident.fingerprint);
|
|
138
|
+
merged.set(
|
|
139
|
+
incident.fingerprint,
|
|
140
|
+
existing ? mergeIncident(existing, incident) : incident,
|
|
141
|
+
);
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
const incidents = [...merged.values()]
|
|
146
|
+
.sort((a, b) => {
|
|
147
|
+
if (a.severity !== b.severity) return a.severity === "error" ? -1 : 1;
|
|
148
|
+
return b.lastSeen.localeCompare(a.lastSeen);
|
|
149
|
+
})
|
|
150
|
+
.slice(0, limit);
|
|
151
|
+
|
|
152
|
+
return { incidents, truncated, scannedFiles };
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
/** The days a query may read, oldest first. */
|
|
156
|
+
private dayRange(since?: string): string[] {
|
|
157
|
+
const days: string[] = [];
|
|
158
|
+
const end = new Date();
|
|
159
|
+
const start = new Date(end.getTime() - (this.maxScanDays - 1) * 86_400_000);
|
|
160
|
+
if (since) {
|
|
161
|
+
const parsed = new Date(since);
|
|
162
|
+
if (!Number.isNaN(parsed.getTime()) && parsed > start) start.setTime(parsed.getTime());
|
|
163
|
+
}
|
|
164
|
+
for (let day = new Date(start); day <= end; day.setTime(day.getTime() + 86_400_000)) {
|
|
165
|
+
days.push(toIsoDay(day));
|
|
166
|
+
}
|
|
167
|
+
return days;
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
/** Does the incident match the filters of the query? */
|
|
171
|
+
private matches(incident: LogIncident, params: IncidentQueryParams): boolean {
|
|
172
|
+
if (incident.tenantId !== params.tenantId) return false;
|
|
173
|
+
if (params.severity && incident.severity !== params.severity) return false;
|
|
174
|
+
if (params.source && incident.source !== params.source) return false;
|
|
175
|
+
if (params.event && incident.event !== params.event) return false;
|
|
176
|
+
if (params.since && incident.lastSeen < params.since) return false;
|
|
177
|
+
if (params.until && incident.lastSeen >= params.until) return false;
|
|
178
|
+
return true;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
/** The tenant directories of the store. Used by the maintenance tests. */
|
|
182
|
+
tenants(): string[] {
|
|
183
|
+
if (!existsSync(this.dir)) return [];
|
|
184
|
+
try {
|
|
185
|
+
return readdirSync(this.dir, { withFileTypes: true })
|
|
186
|
+
.filter((entry) => entry.isDirectory())
|
|
187
|
+
.map((entry) => entry.name);
|
|
188
|
+
} catch {
|
|
189
|
+
return [];
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}
|
|
@@ -54,3 +54,24 @@ export type {
|
|
|
54
54
|
|
|
55
55
|
export { createLogHttpHandler } from "./http.js";
|
|
56
56
|
export type { LogHttpHandler, LogHttpOptions } from "./http.js";
|
|
57
|
+
|
|
58
|
+
export { IncidentStore } from "./incident-store.js";
|
|
59
|
+
export type {
|
|
60
|
+
IncidentQueryParams,
|
|
61
|
+
IncidentQueryResult,
|
|
62
|
+
IncidentStoreOptions,
|
|
63
|
+
} from "./incident-store.js";
|
|
64
|
+
|
|
65
|
+
export {
|
|
66
|
+
INCIDENT_COLLECTION_NAME,
|
|
67
|
+
IncidentQdrantWriter,
|
|
68
|
+
incidentPointId,
|
|
69
|
+
incidentVector,
|
|
70
|
+
tenantFilter,
|
|
71
|
+
toIncidentPayload,
|
|
72
|
+
} from "./incident-qdrant.js";
|
|
73
|
+
export type {
|
|
74
|
+
IncidentPayload,
|
|
75
|
+
IncidentPoint,
|
|
76
|
+
QdrantLike,
|
|
77
|
+
} from "./incident-qdrant.js";
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
*/
|
|
12
12
|
|
|
13
13
|
import { validateBatch, type BatchValidationLimits } from "../ingest/schema.js";
|
|
14
|
+
import { extractIncidents, type LogIncident } from "../incidents/schema.js";
|
|
14
15
|
import {
|
|
15
16
|
LOG_READ_SCOPE,
|
|
16
17
|
LOG_WRITE_SCOPE,
|
|
@@ -19,6 +20,8 @@ import {
|
|
|
19
20
|
} from "./credentials.js";
|
|
20
21
|
import { serverObjectKey } from "./keys.js";
|
|
21
22
|
import type { LogIndexStore, LogQueryParams, LogQueryResult } from "./index-store.js";
|
|
23
|
+
import type { IncidentQueryParams, IncidentStore } from "./incident-store.js";
|
|
24
|
+
import type { IncidentQdrantWriter } from "./incident-qdrant.js";
|
|
22
25
|
import type { LogOutbox, OutboxBatch } from "./outbox.js";
|
|
23
26
|
|
|
24
27
|
export interface IngestSuccess {
|
|
@@ -52,20 +55,35 @@ export interface LogIngestServiceOptions {
|
|
|
52
55
|
credentials: LogCredentialStore;
|
|
53
56
|
outbox: LogOutbox;
|
|
54
57
|
index: LogIndexStore;
|
|
58
|
+
/** Durable storage of the derived incidents. Optional. */
|
|
59
|
+
incidents?: IncidentStore;
|
|
60
|
+
/** Searchable view of the incidents. Optional. */
|
|
61
|
+
incidentIndex?: IncidentQdrantWriter;
|
|
55
62
|
/** Validation limits for an inbound batch. */
|
|
56
63
|
limits?: Partial<BatchValidationLimits>;
|
|
57
64
|
}
|
|
58
65
|
|
|
66
|
+
export interface IncidentQuerySuccess {
|
|
67
|
+
incidents: LogIncident[];
|
|
68
|
+
truncated: boolean;
|
|
69
|
+
scannedFiles: number;
|
|
70
|
+
tenantId: string;
|
|
71
|
+
}
|
|
72
|
+
|
|
59
73
|
export class LogIngestService {
|
|
60
74
|
private readonly credentials: LogCredentialStore;
|
|
61
75
|
private readonly outbox: LogOutbox;
|
|
62
76
|
private readonly index: LogIndexStore;
|
|
77
|
+
private readonly incidents: IncidentStore | undefined;
|
|
78
|
+
private readonly incidentIndex: IncidentQdrantWriter | undefined;
|
|
63
79
|
private readonly limits: Partial<BatchValidationLimits>;
|
|
64
80
|
|
|
65
81
|
constructor(options: LogIngestServiceOptions) {
|
|
66
82
|
this.credentials = options.credentials;
|
|
67
83
|
this.outbox = options.outbox;
|
|
68
84
|
this.index = options.index;
|
|
85
|
+
this.incidents = options.incidents;
|
|
86
|
+
this.incidentIndex = options.incidentIndex;
|
|
69
87
|
this.limits = options.limits ?? {};
|
|
70
88
|
}
|
|
71
89
|
|
|
@@ -136,6 +154,9 @@ export class LogIngestService {
|
|
|
136
154
|
// The metadata index is best effort: a failing index never loses
|
|
137
155
|
// the batch itself.
|
|
138
156
|
this.index.append(batch, serverObjectKey(batch));
|
|
157
|
+
// The same holds for the derived incidents: they are a view of
|
|
158
|
+
// the batch, never a precondition for accepting it.
|
|
159
|
+
this.recordIncidents(batch);
|
|
139
160
|
return {
|
|
140
161
|
status: 202,
|
|
141
162
|
body: {
|
|
@@ -193,4 +214,62 @@ export class LogIngestService {
|
|
|
193
214
|
if (result.nextCursor) body.nextCursor = result.nextCursor;
|
|
194
215
|
return { status: 200, body };
|
|
195
216
|
}
|
|
217
|
+
|
|
218
|
+
/**
|
|
219
|
+
* Derive the incidents of a batch and store them.
|
|
220
|
+
*
|
|
221
|
+
* The tenant comes from the credential that was authenticated, never
|
|
222
|
+
* from the batch itself. A failing store or a failing Qdrant never
|
|
223
|
+
* affects the acceptance of the batch.
|
|
224
|
+
*/
|
|
225
|
+
private recordIncidents(batch: OutboxBatch): void {
|
|
226
|
+
if (!this.incidents && !this.incidentIndex) return;
|
|
227
|
+
const derived = extractIncidents(batch.records, batch.tenantId, batch.installationId);
|
|
228
|
+
if (derived.length === 0) return;
|
|
229
|
+
if (this.incidents) this.incidents.append(derived);
|
|
230
|
+
if (this.incidentIndex) void this.incidentIndex.upsert(derived);
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
/**
|
|
234
|
+
* Query the incidents of the tenant of the caller.
|
|
235
|
+
*
|
|
236
|
+
* The `tenantId` of the request is ignored on purpose - only the
|
|
237
|
+
* credential decides whose incidents are visible.
|
|
238
|
+
*/
|
|
239
|
+
queryIncidents(
|
|
240
|
+
params: Omit<IncidentQueryParams, "tenantId">,
|
|
241
|
+
bearerToken: string | undefined,
|
|
242
|
+
): { status: number; body: IncidentQuerySuccess | IngestFailure } {
|
|
243
|
+
if (!this.credentials.configured) {
|
|
244
|
+
return {
|
|
245
|
+
status: 503,
|
|
246
|
+
body: { error: "log ingest is not configured", code: "ingest_unconfigured" },
|
|
247
|
+
};
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
const auth = this.credentials.authenticate(bearerToken);
|
|
251
|
+
if (!auth) {
|
|
252
|
+
return { status: 401, body: { error: "unauthorized", code: "unauthorized" } };
|
|
253
|
+
}
|
|
254
|
+
if (!auth.scopes.includes(LOG_READ_SCOPE)) {
|
|
255
|
+
return { status: 403, body: { error: "forbidden", code: "forbidden" } };
|
|
256
|
+
}
|
|
257
|
+
if (!this.incidents) {
|
|
258
|
+
return {
|
|
259
|
+
status: 503,
|
|
260
|
+
body: { error: "incident storage is not configured", code: "incidents_unconfigured" },
|
|
261
|
+
};
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
const result = this.incidents.query({ ...params, tenantId: auth.tenantId });
|
|
265
|
+
return {
|
|
266
|
+
status: 200,
|
|
267
|
+
body: {
|
|
268
|
+
incidents: result.incidents,
|
|
269
|
+
truncated: result.truncated,
|
|
270
|
+
scannedFiles: result.scannedFiles,
|
|
271
|
+
tenantId: auth.tenantId,
|
|
272
|
+
},
|
|
273
|
+
};
|
|
274
|
+
}
|
|
196
275
|
}
|
|
@@ -2,9 +2,25 @@
|
|
|
2
2
|
* The shipper owns the delivery decision.
|
|
3
3
|
*
|
|
4
4
|
* Producers call `log()`. The shipper redacts, samples, buffers, and then
|
|
5
|
-
* delivers a batch through the configured transports
|
|
5
|
+
* delivers a batch through the configured transports.
|
|
6
6
|
*
|
|
7
|
-
*
|
|
7
|
+
* Two delivery modes exist:
|
|
8
|
+
*
|
|
9
|
+
* fallback (the default) - the transports form a chain. The first
|
|
10
|
+
* transport that accepts the batch wins and the later ones are not
|
|
11
|
+
* called:
|
|
12
|
+
*
|
|
13
|
+
* R2 (durable archive) -> webhook (live) -> local spool
|
|
14
|
+
*
|
|
15
|
+
* fanout (explicit opt-in) - the transports are independent. Every
|
|
16
|
+
* transport receives the batch, each one tracks its own success, and
|
|
17
|
+
* the batch is spooled only when EVERY transport failed:
|
|
18
|
+
*
|
|
19
|
+
* R2 (durable archive) + webhook (live) -> local spool
|
|
20
|
+
*
|
|
21
|
+
* Fallback is the default because it avoids duplicate records in the
|
|
22
|
+
* archive. Fanout is opt-in because it deliberately creates a second copy
|
|
23
|
+
* of every batch.
|
|
8
24
|
*
|
|
9
25
|
* If every transport fails the batch is spooled to disk and retried on the
|
|
10
26
|
* next flush, so a temporary outage costs latency, not data.
|
|
@@ -31,6 +47,28 @@ import {
|
|
|
31
47
|
type LogTransport,
|
|
32
48
|
} from "./types.js";
|
|
33
49
|
|
|
50
|
+
/**
|
|
51
|
+
* How the batch is handed to the transports.
|
|
52
|
+
*
|
|
53
|
+
* - `fallback`: the first transport that accepts the batch wins.
|
|
54
|
+
* - `fanout`: every transport receives the batch independently.
|
|
55
|
+
*/
|
|
56
|
+
export type DeliveryMode = "fallback" | "fanout";
|
|
57
|
+
|
|
58
|
+
/** The delivery state of one transport. */
|
|
59
|
+
export interface TransportStatus {
|
|
60
|
+
/** The name of the transport. */
|
|
61
|
+
name: string;
|
|
62
|
+
/** How many batches this transport accepted. */
|
|
63
|
+
delivered: number;
|
|
64
|
+
/** How many batches this transport rejected. */
|
|
65
|
+
failed: number;
|
|
66
|
+
/** The message of the last failure. */
|
|
67
|
+
lastError?: string;
|
|
68
|
+
/** ISO timestamp of the last successful delivery. */
|
|
69
|
+
lastSuccessAt?: string;
|
|
70
|
+
}
|
|
71
|
+
|
|
34
72
|
export interface LogShipperOptions {
|
|
35
73
|
/** Application name reported with every batch. */
|
|
36
74
|
app?: string;
|
|
@@ -47,6 +85,12 @@ export interface LogShipperOptions {
|
|
|
47
85
|
sessionId?: string;
|
|
48
86
|
/** Transports in priority order. */
|
|
49
87
|
transports?: LogTransport[];
|
|
88
|
+
/**
|
|
89
|
+
* How the transports are used. `fallback` (the default) lets the first
|
|
90
|
+
* transport that accepts the batch win; `fanout` delivers the batch to
|
|
91
|
+
* every transport independently.
|
|
92
|
+
*/
|
|
93
|
+
delivery?: DeliveryMode;
|
|
50
94
|
/** Local spool used when every transport fails. */
|
|
51
95
|
spool?: LogSpool;
|
|
52
96
|
/** Buffer bounds. */
|
|
@@ -86,6 +130,8 @@ export class LogShipper {
|
|
|
86
130
|
private readonly hostLabel: string | undefined;
|
|
87
131
|
private readonly sessionId: string | undefined;
|
|
88
132
|
private readonly transports: LogTransport[];
|
|
133
|
+
private readonly delivery: DeliveryMode;
|
|
134
|
+
private readonly transportStatus = new Map<string, TransportStatus>();
|
|
89
135
|
private readonly spool: LogSpool | undefined;
|
|
90
136
|
private readonly buffer: LogBuffer;
|
|
91
137
|
private readonly sampler: LogSampler;
|
|
@@ -112,6 +158,7 @@ export class LogShipper {
|
|
|
112
158
|
this.hostLabel = options.hostLabel ?? hostname();
|
|
113
159
|
this.sessionId = options.sessionId;
|
|
114
160
|
this.transports = options.transports ?? [];
|
|
161
|
+
this.delivery = options.delivery ?? "fallback";
|
|
115
162
|
this.spool = options.spool;
|
|
116
163
|
this.buffer = new LogBuffer(options.buffer);
|
|
117
164
|
this.sampler = new LogSampler(options.sampling);
|
|
@@ -221,6 +268,21 @@ export class LogShipper {
|
|
|
221
268
|
};
|
|
222
269
|
}
|
|
223
270
|
|
|
271
|
+
/**
|
|
272
|
+
* The delivery state of every transport.
|
|
273
|
+
*
|
|
274
|
+
* In fanout mode this is the only way to see that one transport is
|
|
275
|
+
* broken while the others still deliver.
|
|
276
|
+
*/
|
|
277
|
+
getTransportStatus(): TransportStatus[] {
|
|
278
|
+
return [...this.transportStatus.values()].map((status) => ({ ...status }));
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
/** The delivery mode of the shipper. */
|
|
282
|
+
get deliveryMode(): DeliveryMode {
|
|
283
|
+
return this.delivery;
|
|
284
|
+
}
|
|
285
|
+
|
|
224
286
|
private buildRecord(input: LogInput): LogRecord {
|
|
225
287
|
const record: LogRecord = {
|
|
226
288
|
ts: new Date(this.now()).toISOString(),
|
|
@@ -291,20 +353,73 @@ export class LogShipper {
|
|
|
291
353
|
}
|
|
292
354
|
}
|
|
293
355
|
|
|
294
|
-
/**
|
|
356
|
+
/**
|
|
357
|
+
* Deliver the batch to the transports.
|
|
358
|
+
*
|
|
359
|
+
* In `fallback` mode the transports form a chain: the first one that
|
|
360
|
+
* accepts the batch wins and the later ones are not called.
|
|
361
|
+
*
|
|
362
|
+
* In `fanout` mode every transport receives the batch independently.
|
|
363
|
+
* Each transport tracks its own success, so a broken transport does not
|
|
364
|
+
* hide the success of the others. The batch is only lost when EVERY
|
|
365
|
+
* transport failed.
|
|
366
|
+
*/
|
|
295
367
|
private async deliver(batch: LogBatch): Promise<boolean> {
|
|
368
|
+
if (this.delivery === "fanout") return this.deliverToAll(batch);
|
|
296
369
|
for (const transport of this.transports) {
|
|
297
370
|
try {
|
|
298
371
|
await transport.send(batch);
|
|
372
|
+
this.noteSuccess(transport.name);
|
|
299
373
|
return true;
|
|
300
374
|
} catch (error) {
|
|
301
|
-
this.
|
|
302
|
-
error instanceof Error ? error.message : String(error);
|
|
375
|
+
this.noteFailure(transport.name, error);
|
|
303
376
|
}
|
|
304
377
|
}
|
|
305
378
|
return false;
|
|
306
379
|
}
|
|
307
380
|
|
|
381
|
+
/** Deliver the batch to every transport. Returns true when one accepted it. */
|
|
382
|
+
private async deliverToAll(batch: LogBatch): Promise<boolean> {
|
|
383
|
+
let accepted = false;
|
|
384
|
+
for (const transport of this.transports) {
|
|
385
|
+
try {
|
|
386
|
+
await transport.send(batch);
|
|
387
|
+
this.noteSuccess(transport.name);
|
|
388
|
+
accepted = true;
|
|
389
|
+
} catch (error) {
|
|
390
|
+
this.noteFailure(transport.name, error);
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
return accepted;
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
/** Record a successful delivery. */
|
|
397
|
+
private noteSuccess(name: string): void {
|
|
398
|
+
const status = this.statusFor(name);
|
|
399
|
+
status.delivered++;
|
|
400
|
+
status.lastSuccessAt = new Date(this.now()).toISOString();
|
|
401
|
+
delete status.lastError;
|
|
402
|
+
}
|
|
403
|
+
|
|
404
|
+
/** Record a failed delivery. */
|
|
405
|
+
private noteFailure(name: string, error: unknown): void {
|
|
406
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
407
|
+
this.stats.errors[name] = message;
|
|
408
|
+
const status = this.statusFor(name);
|
|
409
|
+
status.failed++;
|
|
410
|
+
status.lastError = message;
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
/** The delivery state of one transport. */
|
|
414
|
+
private statusFor(name: string): TransportStatus {
|
|
415
|
+
let status = this.transportStatus.get(name);
|
|
416
|
+
if (!status) {
|
|
417
|
+
status = { name, delivered: 0, failed: 0 };
|
|
418
|
+
this.transportStatus.set(name, status);
|
|
419
|
+
}
|
|
420
|
+
return status;
|
|
421
|
+
}
|
|
422
|
+
|
|
308
423
|
/** Re-send spooled files. Stops at the first failure. */
|
|
309
424
|
private async drainSpool(): Promise<void> {
|
|
310
425
|
if (!this.spool) return;
|