@wrongstack/core 0.297.0 → 0.298.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/chronicle/index.js +126 -22
- package/dist/chronicle/project-server-client.d.ts +12 -0
- package/dist/chronicle/project-server-protocol.d.ts +22 -0
- package/dist/chronicle/project-server.js +238 -157
- package/dist/coordination/agents/index.js +136 -1
- package/dist/coordination/agents/role-skills.d.ts +3 -2
- package/dist/coordination/brain-trace.d.ts +2 -1
- package/dist/coordination/director/director-task-registry.d.ts +12 -0
- package/dist/coordination/fleet-supervisor.d.ts +21 -0
- package/dist/coordination/index.d.ts +23 -21
- package/dist/coordination/index.js +16493 -16068
- package/dist/coordination/mail-tools.d.ts +3 -3
- package/dist/coordination/mailbox-credential-store.d.ts +22 -2
- package/dist/coordination/mailbox-credential-throttle.d.ts +63 -0
- package/dist/coordination/mailbox-project-server-client.d.ts +16 -0
- package/dist/coordination/mailbox-project-server-protocol.d.ts +43 -5
- package/dist/coordination/mailbox-project-server.js +508 -253
- package/dist/coordination/provider-status-tracker.d.ts +2 -0
- package/dist/coordination/remote-mailbox-credential-store.d.ts +5 -5
- package/dist/coordination/remote-mailbox.d.ts +8 -4
- package/dist/coordination/sqlite-mailbox-credentials.d.ts +11 -0
- package/dist/core/fallback-profile-manager.d.ts +14 -0
- package/dist/core/index.js +451 -137
- package/dist/core/instruction-bundle.d.ts +12 -0
- package/dist/core/system-prompt-builder.d.ts +14 -0
- package/dist/core/system-prompt-skill-bodies.d.ts +1 -1
- package/dist/core/system-prompt-skill-text.d.ts +1 -2
- package/dist/defaults/index.js +2081 -1102
- package/dist/design/index.js +47 -8
- package/dist/execution/design-materialize.d.ts +22 -0
- package/dist/execution/index.js +495 -248
- package/dist/execution/skill-loader.d.ts +10 -1
- package/dist/execution/tool-error-taxonomy.d.ts +31 -0
- package/dist/execution/tool-executor.d.ts +1 -0
- package/dist/goal/index.js +3 -1
- package/dist/hooks/index.js +5 -0
- package/dist/hq/auth-audit.d.ts +6 -0
- package/dist/hq/auth-store.d.ts +59 -3
- package/dist/hq/index.js +401 -101
- package/dist/hq/kanban-store.d.ts +3 -0
- package/dist/hq/protocol/core.d.ts +3 -15
- package/dist/hq/protocol/envelope.d.ts +29 -0
- package/dist/hq/protocol/governance.d.ts +34 -0
- package/dist/hq/protocol/project.d.ts +3 -0
- package/dist/hq/protocol/resume.d.ts +1 -1
- package/dist/hq/protocol.d.ts +9 -8
- package/dist/hq/protocol.js +675 -0
- package/dist/index.js +8518 -6416
- package/dist/infrastructure/index.js +198 -101
- package/dist/kernel/events/session-events.d.ts +3 -0
- package/dist/kernel/events/tool-events.d.ts +3 -1
- package/dist/models/index.js +1 -1
- package/dist/observability/index.js +27 -0
- package/dist/observability/prometheus.d.ts +11 -0
- package/dist/plugin/index.d.ts +5 -1
- package/dist/plugin/index.js +950 -509
- package/dist/plugins/review-store-maintenance.d.ts +26 -0
- package/dist/plugins/review-types.d.ts +6 -0
- package/dist/security/capabilities.d.ts +45 -1
- package/dist/security/error-sanitize.d.ts +49 -0
- package/dist/security/file-permissions.d.ts +41 -0
- package/dist/security/index.d.ts +9 -6
- package/dist/security/index.js +3007 -2032
- package/dist/security/permission-policy.d.ts +55 -3
- package/dist/security/secret-vault.d.ts +17 -0
- package/dist/security/totp.d.ts +86 -0
- package/dist/skills/frontmatter.d.ts +12 -1
- package/dist/skills/github-fetcher.d.ts +48 -0
- package/dist/skills/index.js +137 -26
- package/dist/skills/limits.d.ts +19 -0
- package/dist/skills/skill-installer.d.ts +13 -0
- package/dist/storage/index.js +928 -732
- package/dist/storage/provider-config-watcher.d.ts +1 -0
- package/dist/storage/session-helpers.d.ts +1 -0
- package/dist/storage/session-store.d.ts +9 -2
- package/dist/storage/session-workspace-checkpoints.d.ts +5 -0
- package/dist/tools/fallback-manage-tools.d.ts +6 -0
- package/dist/tools/index.js +287 -131
- package/dist/tools/mcp-use.d.ts +1 -1
- package/dist/types/blocks.d.ts +7 -0
- package/dist/types/config/autonomy.d.ts +12 -3
- package/dist/types/config/mcp-features.d.ts +9 -1
- package/dist/types/config/root.d.ts +10 -4
- package/dist/types/context-window.d.ts +15 -0
- package/dist/types/index.d.ts +1 -1
- package/dist/types/secret-vault.d.ts +8 -0
- package/dist/types/session.d.ts +2 -0
- package/dist/types/skill.d.ts +56 -0
- package/dist/types/tool-executor.d.ts +2 -0
- package/dist/utils/env-typed.d.ts +64 -0
- package/dist/utils/glob-match.d.ts +21 -1
- package/dist/utils/heap-watchdog.js +1 -1
- package/dist/utils/incoming-images.d.ts +19 -0
- package/dist/utils/index.d.ts +15 -12
- package/dist/utils/index.js +3083 -2801
- package/dist/utils/path-segment.d.ts +29 -0
- package/dist/utils/win32-cmd.d.ts +25 -0
- package/dist/worktree/index.js +5 -0
- package/package.json +8 -3
- package/skills/chimera/SKILL.md +16 -4
- package/skills/data-governance/SKILL.md +92 -0
- package/skills/wrongstack-kanban/SKILL.md +125 -64
- package/dist/agent-status-helpers.d.ts.map +0 -1
- package/dist/agent-status-tracker.d.ts.map +0 -1
- package/dist/boot.d.ts.map +0 -1
- package/dist/chronicle/context.d.ts.map +0 -1
- package/dist/chronicle/decision-adapter.d.ts.map +0 -1
- package/dist/chronicle/domain-adapter.d.ts.map +0 -1
- package/dist/chronicle/event-hash.d.ts.map +0 -1
- package/dist/chronicle/file-observer.d.ts.map +0 -1
- package/dist/chronicle/health-monitor.d.ts.map +0 -1
- package/dist/chronicle/identity.d.ts.map +0 -1
- package/dist/chronicle/index.d.ts.map +0 -1
- package/dist/chronicle/index.js.map +0 -7
- package/dist/chronicle/journal.d.ts.map +0 -1
- package/dist/chronicle/legacy-journal-import.d.ts.map +0 -1
- package/dist/chronicle/metrics-store.d.ts.map +0 -1
- package/dist/chronicle/partition-filename.d.ts.map +0 -1
- package/dist/chronicle/partition-range-cache.d.ts.map +0 -1
- package/dist/chronicle/process-adapter.d.ts.map +0 -1
- package/dist/chronicle/project-access.d.ts.map +0 -1
- package/dist/chronicle/project-server-client.d.ts.map +0 -1
- package/dist/chronicle/project-server-endpoint.d.ts.map +0 -1
- package/dist/chronicle/project-server-protocol.d.ts.map +0 -1
- package/dist/chronicle/project-server.d.ts.map +0 -1
- package/dist/chronicle/project-server.js.map +0 -7
- package/dist/chronicle/prompt-manifest.d.ts.map +0 -1
- package/dist/chronicle/provider-adapter.d.ts.map +0 -1
- package/dist/chronicle/query.d.ts.map +0 -1
- package/dist/chronicle/review-adapter.d.ts.map +0 -1
- package/dist/chronicle/rollup-adapter.d.ts.map +0 -1
- package/dist/chronicle/sink.d.ts.map +0 -1
- package/dist/chronicle/sqlite-journal.d.ts.map +0 -1
- package/dist/chronicle/sqlite-query.d.ts.map +0 -1
- package/dist/chronicle/stream-adapter.d.ts.map +0 -1
- package/dist/chronicle/tool-adapter.d.ts.map +0 -1
- package/dist/chronicle/types.d.ts.map +0 -1
- package/dist/coordination/adaptive-concurrency.d.ts.map +0 -1
- package/dist/coordination/agent-bridge.d.ts.map +0 -1
- package/dist/coordination/agent-monitor.d.ts.map +0 -1
- package/dist/coordination/agent-subagent-runner.d.ts.map +0 -1
- package/dist/coordination/agents/agent-prompts.d.ts.map +0 -1
- package/dist/coordination/agents/index.d.ts.map +0 -1
- package/dist/coordination/agents/index.js.map +0 -7
- package/dist/coordination/agents/phase1-discovery.d.ts.map +0 -1
- package/dist/coordination/agents/phase2-planning.d.ts.map +0 -1
- package/dist/coordination/agents/phase3-build.d.ts.map +0 -1
- package/dist/coordination/agents/phase3-techstack.d.ts.map +0 -1
- package/dist/coordination/agents/phase3-wave1-platform.d.ts.map +0 -1
- package/dist/coordination/agents/phase3-wave2-meta.d.ts.map +0 -1
- package/dist/coordination/agents/phase4-verify.d.ts.map +0 -1
- package/dist/coordination/agents/phase5-review.d.ts.map +0 -1
- package/dist/coordination/agents/phase6-domain.d.ts.map +0 -1
- package/dist/coordination/agents/phase7-knowledge.d.ts.map +0 -1
- package/dist/coordination/agents/phase8-delivery.d.ts.map +0 -1
- package/dist/coordination/agents/phase8-wave3-products.d.ts.map +0 -1
- package/dist/coordination/agents/phase9-meta.d.ts.map +0 -1
- package/dist/coordination/agents/phase9-wave4-platform-meta.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-config-validation.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-consolidation.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-files.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-identity-types.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-identity.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-knowledge-manifests.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-learning-entries.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-learning-normalize.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-learning-policy.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-learning-structured.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-paths.d.ts.map +0 -1
- package/dist/coordination/agents/project-agent-profile.d.ts.map +0 -1
- package/dist/coordination/agents/role-skills.d.ts.map +0 -1
- package/dist/coordination/agents/types.d.ts.map +0 -1
- package/dist/coordination/agents.d.ts.map +0 -1
- package/dist/coordination/auto-extend.d.ts.map +0 -1
- package/dist/coordination/autonomous-brain.d.ts.map +0 -1
- package/dist/coordination/autonomous-coordinator.d.ts.map +0 -1
- package/dist/coordination/brain-cache.d.ts.map +0 -1
- package/dist/coordination/brain-heuristics.d.ts.map +0 -1
- package/dist/coordination/brain-ledger.d.ts.map +0 -1
- package/dist/coordination/brain-monitor.d.ts.map +0 -1
- package/dist/coordination/brain-rules.d.ts.map +0 -1
- package/dist/coordination/brain-telemetry.d.ts.map +0 -1
- package/dist/coordination/brain-trace.d.ts.map +0 -1
- package/dist/coordination/brain.d.ts.map +0 -1
- package/dist/coordination/change-manager.d.ts.map +0 -1
- package/dist/coordination/checkpoint-wiring.d.ts.map +0 -1
- package/dist/coordination/collab-bus.d.ts.map +0 -1
- package/dist/coordination/collab-debug-types.d.ts.map +0 -1
- package/dist/coordination/collab-debug.d.ts.map +0 -1
- package/dist/coordination/collab-director-host.d.ts.map +0 -1
- package/dist/coordination/commit-safety.d.ts.map +0 -1
- package/dist/coordination/consensus-protocol.d.ts.map +0 -1
- package/dist/coordination/coordinator/error-classifier.d.ts.map +0 -1
- package/dist/coordination/delegate-tool.d.ts.map +0 -1
- package/dist/coordination/dep-watcher-bridge.d.ts.map +0 -1
- package/dist/coordination/dep-watcher.d.ts.map +0 -1
- package/dist/coordination/director/director-btw-notes.d.ts.map +0 -1
- package/dist/coordination/director/director-budget-policy.d.ts.map +0 -1
- package/dist/coordination/director/director-collab.d.ts.map +0 -1
- package/dist/coordination/director/director-errors.d.ts.map +0 -1
- package/dist/coordination/director/director-task-registry.d.ts.map +0 -1
- package/dist/coordination/director/director-toolset.d.ts.map +0 -1
- package/dist/coordination/director-basic-tools.d.ts.map +0 -1
- package/dist/coordination/director-collab-tools.d.ts.map +0 -1
- package/dist/coordination/director-host-contracts.d.ts.map +0 -1
- package/dist/coordination/director-input-helpers.d.ts.map +0 -1
- package/dist/coordination/director-kanban-queue-helpers.d.ts.map +0 -1
- package/dist/coordination/director-options.d.ts.map +0 -1
- package/dist/coordination/director-prompts.d.ts.map +0 -1
- package/dist/coordination/director-quality-gate-tool.d.ts.map +0 -1
- package/dist/coordination/director-session.d.ts.map +0 -1
- package/dist/coordination/director-spawn-model.d.ts.map +0 -1
- package/dist/coordination/director-tools.d.ts.map +0 -1
- package/dist/coordination/director.d.ts.map +0 -1
- package/dist/coordination/dispatcher.d.ts.map +0 -1
- package/dist/coordination/file-author-tracker.d.ts.map +0 -1
- package/dist/coordination/fleet-bus.d.ts.map +0 -1
- package/dist/coordination/fleet-event-validation.d.ts.map +0 -1
- package/dist/coordination/fleet-manager.d.ts.map +0 -1
- package/dist/coordination/fleet-spawn.d.ts.map +0 -1
- package/dist/coordination/fleet-status-tool.d.ts.map +0 -1
- package/dist/coordination/fleet-supervisor.d.ts.map +0 -1
- package/dist/coordination/fleet.d.ts.map +0 -1
- package/dist/coordination/global-mailbox-completion.d.ts.map +0 -1
- package/dist/coordination/global-mailbox-paths.d.ts.map +0 -1
- package/dist/coordination/icoordinator.d.ts.map +0 -1
- package/dist/coordination/ifleet-manager.d.ts.map +0 -1
- package/dist/coordination/in-memory-transport.d.ts.map +0 -1
- package/dist/coordination/index.d.ts.map +0 -1
- package/dist/coordination/index.js.map +0 -7
- package/dist/coordination/knowledge-graph.d.ts.map +0 -1
- package/dist/coordination/large-answer-store.d.ts.map +0 -1
- package/dist/coordination/mail-tools.d.ts.map +0 -1
- package/dist/coordination/mailbox-actions.d.ts.map +0 -1
- package/dist/coordination/mailbox-auth-types.d.ts.map +0 -1
- package/dist/coordination/mailbox-codecs.d.ts.map +0 -1
- package/dist/coordination/mailbox-constants.d.ts.map +0 -1
- package/dist/coordination/mailbox-credential-store.d.ts.map +0 -1
- package/dist/coordination/mailbox-events.d.ts.map +0 -1
- package/dist/coordination/mailbox-health.d.ts.map +0 -1
- package/dist/coordination/mailbox-hooks.d.ts.map +0 -1
- package/dist/coordination/mailbox-http-auth.d.ts.map +0 -1
- package/dist/coordination/mailbox-http-rate-limit.d.ts.map +0 -1
- package/dist/coordination/mailbox-http-router.d.ts.map +0 -1
- package/dist/coordination/mailbox-http-validation.d.ts.map +0 -1
- package/dist/coordination/mailbox-message-codec.d.ts.map +0 -1
- package/dist/coordination/mailbox-parse-state.d.ts.map +0 -1
- package/dist/coordination/mailbox-project-server-client.d.ts.map +0 -1
- package/dist/coordination/mailbox-project-server-endpoint.d.ts.map +0 -1
- package/dist/coordination/mailbox-project-server-protocol.d.ts.map +0 -1
- package/dist/coordination/mailbox-project-server.d.ts.map +0 -1
- package/dist/coordination/mailbox-project-server.js.map +0 -7
- package/dist/coordination/mailbox-receipt-folding.d.ts.map +0 -1
- package/dist/coordination/mailbox-registry-codec.d.ts.map +0 -1
- package/dist/coordination/mailbox-retention-state.d.ts.map +0 -1
- package/dist/coordination/mailbox-status-mappers.d.ts.map +0 -1
- package/dist/coordination/mailbox-tool.d.ts.map +0 -1
- package/dist/coordination/mailbox-type-properties.d.ts.map +0 -1
- package/dist/coordination/mailbox-types.d.ts.map +0 -1
- package/dist/coordination/model-matrix.d.ts.map +0 -1
- package/dist/coordination/multi-agent-coordinator.d.ts.map +0 -1
- package/dist/coordination/multi-agent-timeout.d.ts.map +0 -1
- package/dist/coordination/null-fleet-bus.d.ts.map +0 -1
- package/dist/coordination/package-author-tracker.d.ts.map +0 -1
- package/dist/coordination/package-outdated-watcher.d.ts.map +0 -1
- package/dist/coordination/provider-status-tracker.d.ts.map +0 -1
- package/dist/coordination/remote-mailbox-credential-store.d.ts.map +0 -1
- package/dist/coordination/remote-mailbox.d.ts.map +0 -1
- package/dist/coordination/single-instance-mailbox.d.ts.map +0 -1
- package/dist/coordination/spawn-budget.d.ts.map +0 -1
- package/dist/coordination/sqlite-mailbox-compaction.d.ts.map +0 -1
- package/dist/coordination/sqlite-mailbox-credentials.d.ts.map +0 -1
- package/dist/coordination/sqlite-mailbox-rows.d.ts.map +0 -1
- package/dist/coordination/sqlite-mailbox-schema.d.ts.map +0 -1
- package/dist/coordination/sqlite-mailbox.d.ts.map +0 -1
- package/dist/coordination/subagent-budget.d.ts.map +0 -1
- package/dist/coordination/subagent-nicknames.d.ts.map +0 -1
- package/dist/coordination/subagent-result-tool.d.ts.map +0 -1
- package/dist/coordination/task-auctioneer.d.ts.map +0 -1
- package/dist/coordination/task-dag.d.ts.map +0 -1
- package/dist/coordination/techstack-mailbox-consumer.d.ts.map +0 -1
- package/dist/coordination/transport.d.ts.map +0 -1
- package/dist/coordination/worktree-task-runner.d.ts.map +0 -1
- package/dist/core/agent-internals.d.ts.map +0 -1
- package/dist/core/agent-loop.d.ts.map +0 -1
- package/dist/core/agent-response.d.ts.map +0 -1
- package/dist/core/agent-tools.d.ts.map +0 -1
- package/dist/core/agent-types.d.ts.map +0 -1
- package/dist/core/agent.d.ts.map +0 -1
- package/dist/core/btw.d.ts.map +0 -1
- package/dist/core/context.d.ts.map +0 -1
- package/dist/core/continue-intent.d.ts.map +0 -1
- package/dist/core/continue-to-next-iteration.d.ts.map +0 -1
- package/dist/core/conversation-state.d.ts.map +0 -1
- package/dist/core/fallback-model.d.ts.map +0 -1
- package/dist/core/fallback-profile-manager.d.ts.map +0 -1
- package/dist/core/fleet-pulse.d.ts.map +0 -1
- package/dist/core/index.d.ts.map +0 -1
- package/dist/core/index.js.map +0 -7
- package/dist/core/input-builder.d.ts.map +0 -1
- package/dist/core/instruction-bundle.d.ts.map +0 -1
- package/dist/core/iteration-limit.d.ts.map +0 -1
- package/dist/core/mailbox-loop.d.ts.map +0 -1
- package/dist/core/model-availability-calendar.d.ts.map +0 -1
- package/dist/core/model-ref.d.ts.map +0 -1
- package/dist/core/model-ref.js.map +0 -7
- package/dist/core/modes/brief.d.ts.map +0 -1
- package/dist/core/modes/default.d.ts.map +0 -1
- package/dist/core/modes/teach.d.ts.map +0 -1
- package/dist/core/provider-runner.d.ts.map +0 -1
- package/dist/core/queued-messages.d.ts.map +0 -1
- package/dist/core/request-provider-binding.d.ts.map +0 -1
- package/dist/core/run-env.d.ts.map +0 -1
- package/dist/core/streaming-response-builder.d.ts.map +0 -1
- package/dist/core/system-prompt-blocks.d.ts.map +0 -1
- package/dist/core/system-prompt-builder.d.ts.map +0 -1
- package/dist/core/system-prompt-environment-probes.d.ts.map +0 -1
- package/dist/core/system-prompt-environment.d.ts.map +0 -1
- package/dist/core/system-prompt-memory-skills.d.ts.map +0 -1
- package/dist/core/system-prompt-plan.d.ts.map +0 -1
- package/dist/core/system-prompt-shell.d.ts.map +0 -1
- package/dist/core/system-prompt-skill-bodies.d.ts.map +0 -1
- package/dist/core/system-prompt-skill-text.d.ts.map +0 -1
- package/dist/defaults/index.d.ts.map +0 -1
- package/dist/defaults/index.js.map +0 -7
- package/dist/design/index.d.ts.map +0 -1
- package/dist/design/index.js.map +0 -7
- package/dist/execution/auto-compaction-middleware.d.ts.map +0 -1
- package/dist/execution/autonomous-runner.d.ts.map +0 -1
- package/dist/execution/autonomy-brain.d.ts.map +0 -1
- package/dist/execution/autonomy-prompt-contributor.d.ts.map +0 -1
- package/dist/execution/brain-chain.d.ts.map +0 -1
- package/dist/execution/brain-circuit.d.ts.map +0 -1
- package/dist/execution/brain-evaluation.d.ts.map +0 -1
- package/dist/execution/brain-runtime-constants.d.ts.map +0 -1
- package/dist/execution/brain-runtime.d.ts.map +0 -1
- package/dist/execution/compaction-core.d.ts.map +0 -1
- package/dist/execution/compaction-scoring.d.ts.map +0 -1
- package/dist/execution/compaction-summary-cache.d.ts.map +0 -1
- package/dist/execution/compactor.d.ts.map +0 -1
- package/dist/execution/council-brain.d.ts.map +0 -1
- package/dist/execution/council-orchestrator.d.ts.map +0 -1
- package/dist/execution/council-personas.d.ts.map +0 -1
- package/dist/execution/council-profiles.d.ts.map +0 -1
- package/dist/execution/council-prompts.d.ts.map +0 -1
- package/dist/execution/council-resolution.d.ts.map +0 -1
- package/dist/execution/design-color.d.ts.map +0 -1
- package/dist/execution/design-detect.d.ts.map +0 -1
- package/dist/execution/design-kit-loader.d.ts.map +0 -1
- package/dist/execution/design-materialize.d.ts.map +0 -1
- package/dist/execution/design-project-store.d.ts.map +0 -1
- package/dist/execution/design-tune.d.ts.map +0 -1
- package/dist/execution/design-verify.d.ts.map +0 -1
- package/dist/execution/enhance-recovery.d.ts.map +0 -1
- package/dist/execution/error-handler.d.ts.map +0 -1
- package/dist/execution/eternal-autonomy-types.d.ts.map +0 -1
- package/dist/execution/eternal-autonomy.d.ts.map +0 -1
- package/dist/execution/goal-preamble.d.ts.map +0 -1
- package/dist/execution/index.d.ts.map +0 -1
- package/dist/execution/index.js.map +0 -7
- package/dist/execution/intelligent-compactor.d.ts.map +0 -1
- package/dist/execution/model-runtime.d.ts.map +0 -1
- package/dist/execution/one-shot-llm.d.ts.map +0 -1
- package/dist/execution/parallel-eternal-engine.d.ts.map +0 -1
- package/dist/execution/prompt-enhancer.d.ts.map +0 -1
- package/dist/execution/prompt-enhancer.js.map +0 -7
- package/dist/execution/prompt-loader.d.ts.map +0 -1
- package/dist/execution/provider-runner-impl.d.ts.map +0 -1
- package/dist/execution/regex-patterns.d.ts.map +0 -1
- package/dist/execution/retry-policy.d.ts.map +0 -1
- package/dist/execution/selective-compactor.d.ts.map +0 -1
- package/dist/execution/skill-loader.d.ts.map +0 -1
- package/dist/execution/strategy-compactor.d.ts.map +0 -1
- package/dist/execution/subagent-compaction.d.ts.map +0 -1
- package/dist/execution/tool-executor-logging.d.ts.map +0 -1
- package/dist/execution/tool-executor-results.d.ts.map +0 -1
- package/dist/execution/tool-executor-stream.d.ts.map +0 -1
- package/dist/execution/tool-executor-support.d.ts.map +0 -1
- package/dist/execution/tool-executor.d.ts.map +0 -1
- package/dist/extension/extension-points.d.ts.map +0 -1
- package/dist/extension/index.d.ts.map +0 -1
- package/dist/extension/index.js.map +0 -7
- package/dist/extension/registry.d.ts.map +0 -1
- package/dist/fleet-notifier.d.ts.map +0 -1
- package/dist/goal/checkpoint.d.ts.map +0 -1
- package/dist/goal/goal-assessor.d.ts.map +0 -1
- package/dist/goal/goal-planner.d.ts.map +0 -1
- package/dist/goal/goal-runner.d.ts.map +0 -1
- package/dist/goal/index.d.ts.map +0 -1
- package/dist/goal/index.js.map +0 -7
- package/dist/goal/phase-board-mutations.d.ts.map +0 -1
- package/dist/goal/phase-graph-builder.d.ts.map +0 -1
- package/dist/goal/phase-orchestrator-integration.d.ts.map +0 -1
- package/dist/goal/phase-orchestrator-queries.d.ts.map +0 -1
- package/dist/goal/phase-orchestrator-runtime.d.ts.map +0 -1
- package/dist/goal/phase-orchestrator-types.d.ts.map +0 -1
- package/dist/goal/phase-orchestrator.d.ts.map +0 -1
- package/dist/goal/phase-store.d.ts.map +0 -1
- package/dist/goal/types.d.ts.map +0 -1
- package/dist/hooks/http-executor.d.ts.map +0 -1
- package/dist/hooks/index.d.ts.map +0 -1
- package/dist/hooks/index.js.map +0 -7
- package/dist/hooks/registry.d.ts.map +0 -1
- package/dist/hooks/runner.d.ts.map +0 -1
- package/dist/hooks/shell-executor.d.ts.map +0 -1
- package/dist/hooks/shell-hooks-equal.d.ts.map +0 -1
- package/dist/hq/alerts.d.ts.map +0 -1
- package/dist/hq/auth-audit.d.ts.map +0 -1
- package/dist/hq/auth-store.d.ts.map +0 -1
- package/dist/hq/bootstrap-store.d.ts.map +0 -1
- package/dist/hq/brain-bridge.d.ts.map +0 -1
- package/dist/hq/bridge-context.d.ts.map +0 -1
- package/dist/hq/commands.d.ts.map +0 -1
- package/dist/hq/cost-bridge.d.ts.map +0 -1
- package/dist/hq/exposure.d.ts.map +0 -1
- package/dist/hq/factory.d.ts.map +0 -1
- package/dist/hq/fleet-bridge.d.ts.map +0 -1
- package/dist/hq/index.d.ts.map +0 -1
- package/dist/hq/index.js.map +0 -7
- package/dist/hq/kanban-store.d.ts.map +0 -1
- package/dist/hq/mailbox-mapper.d.ts.map +0 -1
- package/dist/hq/persistence/event-log.d.ts.map +0 -1
- package/dist/hq/persistence/jsonl-io.d.ts.map +0 -1
- package/dist/hq/persistence/simple-log.d.ts.map +0 -1
- package/dist/hq/persistence/snapshot-store.d.ts.map +0 -1
- package/dist/hq/persistence/timeseries-store.d.ts.map +0 -1
- package/dist/hq/persistence.d.ts.map +0 -1
- package/dist/hq/protocol/brain.d.ts.map +0 -1
- package/dist/hq/protocol/browser.d.ts.map +0 -1
- package/dist/hq/protocol/client.d.ts.map +0 -1
- package/dist/hq/protocol/core.d.ts.map +0 -1
- package/dist/hq/protocol/fleet.d.ts.map +0 -1
- package/dist/hq/protocol/kanban.d.ts.map +0 -1
- package/dist/hq/protocol/mailbox.d.ts.map +0 -1
- package/dist/hq/protocol/mcp.d.ts.map +0 -1
- package/dist/hq/protocol/peer.d.ts.map +0 -1
- package/dist/hq/protocol/project.d.ts.map +0 -1
- package/dist/hq/protocol/resume.d.ts.map +0 -1
- package/dist/hq/protocol/session.d.ts.map +0 -1
- package/dist/hq/protocol/tool.d.ts.map +0 -1
- package/dist/hq/protocol.d.ts.map +0 -1
- package/dist/hq/publisher.d.ts.map +0 -1
- package/dist/hq/redaction.d.ts.map +0 -1
- package/dist/hq/session-bridge.d.ts.map +0 -1
- package/dist/hq/tool-bridge.d.ts.map +0 -1
- package/dist/hq/transcript-mapper.d.ts.map +0 -1
- package/dist/hq/worktree-bridge.d.ts.map +0 -1
- package/dist/hq/write-queues.d.ts.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -7
- package/dist/infrastructure/context-manager.d.ts.map +0 -1
- package/dist/infrastructure/index.d.ts.map +0 -1
- package/dist/infrastructure/index.js.map +0 -7
- package/dist/infrastructure/logger.d.ts.map +0 -1
- package/dist/infrastructure/mcp-servers.d.ts.map +0 -1
- package/dist/infrastructure/path-resolver.d.ts.map +0 -1
- package/dist/infrastructure/provider-cache-ledger.d.ts.map +0 -1
- package/dist/infrastructure/token-counter.d.ts.map +0 -1
- package/dist/kernel/container.d.ts.map +0 -1
- package/dist/kernel/events/agent-events.d.ts.map +0 -1
- package/dist/kernel/events/brain-events.d.ts.map +0 -1
- package/dist/kernel/events/file-events.d.ts.map +0 -1
- package/dist/kernel/events/fleet-events.d.ts.map +0 -1
- package/dist/kernel/events/memory-events.d.ts.map +0 -1
- package/dist/kernel/events/network-events.d.ts.map +0 -1
- package/dist/kernel/events/process-events.d.ts.map +0 -1
- package/dist/kernel/events/provider-events.d.ts.map +0 -1
- package/dist/kernel/events/sdd-events.d.ts.map +0 -1
- package/dist/kernel/events/session-events.d.ts.map +0 -1
- package/dist/kernel/events/tool-events.d.ts.map +0 -1
- package/dist/kernel/events/worktree-events.d.ts.map +0 -1
- package/dist/kernel/events.d.ts.map +0 -1
- package/dist/kernel/index.d.ts.map +0 -1
- package/dist/kernel/index.js.map +0 -7
- package/dist/kernel/pipeline.d.ts.map +0 -1
- package/dist/kernel/run-controller.d.ts.map +0 -1
- package/dist/kernel/tokens.d.ts.map +0 -1
- package/dist/mailbox-attach.d.ts.map +0 -1
- package/dist/middleware/collab-pause.d.ts.map +0 -1
- package/dist/models/alibaba-token-plan-catalog.d.ts.map +0 -1
- package/dist/models/codex-catalog.d.ts.map +0 -1
- package/dist/models/index.d.ts.map +0 -1
- package/dist/models/index.js.map +0 -7
- package/dist/models/llm-selector.d.ts.map +0 -1
- package/dist/models/mode-store.d.ts.map +0 -1
- package/dist/models/model-intelligence.d.ts.map +0 -1
- package/dist/models/model-router.d.ts.map +0 -1
- package/dist/models/models-registry.d.ts.map +0 -1
- package/dist/models/provider-model-resolve.d.ts.map +0 -1
- package/dist/notifications/index.d.ts.map +0 -1
- package/dist/notifications/index.js.map +0 -7
- package/dist/notifications/notifier-impl.d.ts.map +0 -1
- package/dist/notifications/notifier.d.ts.map +0 -1
- package/dist/notifications/types.d.ts.map +0 -1
- package/dist/observability/event-bridge.d.ts.map +0 -1
- package/dist/observability/health.d.ts.map +0 -1
- package/dist/observability/index.d.ts.map +0 -1
- package/dist/observability/index.js.map +0 -7
- package/dist/observability/metrics.d.ts.map +0 -1
- package/dist/observability/network-telemetry.d.ts.map +0 -1
- package/dist/observability/otel-tracer.d.ts.map +0 -1
- package/dist/observability/otlp-metrics.d.ts.map +0 -1
- package/dist/observability/otlp-traces.d.ts.map +0 -1
- package/dist/observability/process-telemetry.d.ts.map +0 -1
- package/dist/observability/prometheus.d.ts.map +0 -1
- package/dist/observability/redact-command.d.ts.map +0 -1
- package/dist/observability/tracer.d.ts.map +0 -1
- package/dist/plugin/api.d.ts.map +0 -1
- package/dist/plugin/config.d.ts.map +0 -1
- package/dist/plugin/index.d.ts.map +0 -1
- package/dist/plugin/index.js.map +0 -7
- package/dist/plugin/loader.d.ts.map +0 -1
- package/dist/plugins/auto-review-plugin.d.ts.map +0 -1
- package/dist/plugins/chimera-plugin.d.ts.map +0 -1
- package/dist/plugins/prompts-plugin.d.ts.map +0 -1
- package/dist/plugins/review-claim-registry.d.ts.map +0 -1
- package/dist/plugins/review-context-builder.d.ts.map +0 -1
- package/dist/plugins/review-finding-commands.d.ts.map +0 -1
- package/dist/plugins/review-finding-integration.d.ts.map +0 -1
- package/dist/plugins/review-finding-parser.d.ts.map +0 -1
- package/dist/plugins/review-finding-store.d.ts.map +0 -1
- package/dist/plugins/review-finding-types.d.ts.map +0 -1
- package/dist/plugins/review-report-integration.d.ts.map +0 -1
- package/dist/plugins/review-report-store.d.ts.map +0 -1
- package/dist/plugins/review-report-types.d.ts.map +0 -1
- package/dist/plugins/review-types.d.ts.map +0 -1
- package/dist/plugins/skills-plugin.d.ts.map +0 -1
- package/dist/plugins/sync-plugin.d.ts.map +0 -1
- package/dist/prompts/index.d.ts.map +0 -1
- package/dist/prompts/prompt-installer.d.ts.map +0 -1
- package/dist/prompts/prompt-manifest-store.d.ts.map +0 -1
- package/dist/registry/index.d.ts.map +0 -1
- package/dist/registry/index.js.map +0 -7
- package/dist/registry/provider-registry.d.ts.map +0 -1
- package/dist/registry/slash-command-registry.d.ts.map +0 -1
- package/dist/registry/tool-registry.d.ts.map +0 -1
- package/dist/replay/hash.d.ts.map +0 -1
- package/dist/replay/index.d.ts.map +0 -1
- package/dist/replay/index.js.map +0 -7
- package/dist/replay/replay-provider-runner.d.ts.map +0 -1
- package/dist/security/capabilities.d.ts.map +0 -1
- package/dist/security/config-secrets.d.ts.map +0 -1
- package/dist/security/directory-permission-policy.d.ts.map +0 -1
- package/dist/security/directory-policy-schema.d.ts.map +0 -1
- package/dist/security/index.d.ts.map +0 -1
- package/dist/security/index.js.map +0 -7
- package/dist/security/kanban-boundary.d.ts.map +0 -1
- package/dist/security/permission-policy-schema.d.ts.map +0 -1
- package/dist/security/permission-policy.d.ts.map +0 -1
- package/dist/security/readonly-permission-policy.d.ts.map +0 -1
- package/dist/security/secret-scrubber.d.ts.map +0 -1
- package/dist/security/secret-vault.d.ts.map +0 -1
- package/dist/security/trust-boundary.d.ts.map +0 -1
- package/dist/security/yolo-risk.d.ts.map +0 -1
- package/dist/session-registry-atomic-file.d.ts.map +0 -1
- package/dist/session-registry-types.d.ts.map +0 -1
- package/dist/session-registry.d.ts.map +0 -1
- package/dist/skills/foreign-sources.d.ts.map +0 -1
- package/dist/skills/frontmatter.d.ts.map +0 -1
- package/dist/skills/github-fetcher.d.ts.map +0 -1
- package/dist/skills/index.d.ts.map +0 -1
- package/dist/skills/index.js.map +0 -7
- package/dist/skills/limits.d.ts.map +0 -1
- package/dist/skills/manifest-store.d.ts.map +0 -1
- package/dist/skills/registry/github-direct-adapter.d.ts.map +0 -1
- package/dist/skills/registry/registry-adapter.d.ts.map +0 -1
- package/dist/skills/registry/skills-sh-adapter.d.ts.map +0 -1
- package/dist/skills/skill-generator.d.ts.map +0 -1
- package/dist/skills/skill-installer.d.ts.map +0 -1
- package/dist/storage/annotations-store.d.ts.map +0 -1
- package/dist/storage/attachment-store.d.ts.map +0 -1
- package/dist/storage/cloud-sync.d.ts.map +0 -1
- package/dist/storage/completed-work-checkpoint.d.ts.map +0 -1
- package/dist/storage/config-loader/bootstrap.d.ts.map +0 -1
- package/dist/storage/config-loader/default-repair.d.ts.map +0 -1
- package/dist/storage/config-loader/defaults.d.ts.map +0 -1
- package/dist/storage/config-loader/diagnostics.d.ts.map +0 -1
- package/dist/storage/config-loader/env-overrides.d.ts.map +0 -1
- package/dist/storage/config-loader/in-project-policy.d.ts.map +0 -1
- package/dist/storage/config-loader/inline-provider-models.d.ts.map +0 -1
- package/dist/storage/config-loader/legacy-sage-migration.d.ts.map +0 -1
- package/dist/storage/config-loader/path-identity.d.ts.map +0 -1
- package/dist/storage/config-loader/types.d.ts.map +0 -1
- package/dist/storage/config-loader/validation.d.ts.map +0 -1
- package/dist/storage/config-loader.d.ts.map +0 -1
- package/dist/storage/config-migration.d.ts.map +0 -1
- package/dist/storage/config-store.d.ts.map +0 -1
- package/dist/storage/director-state.d.ts.map +0 -1
- package/dist/storage/file-session-writer.d.ts.map +0 -1
- package/dist/storage/goal-coordination.d.ts.map +0 -1
- package/dist/storage/goal-kanban.d.ts.map +0 -1
- package/dist/storage/goal-store.d.ts.map +0 -1
- package/dist/storage/index.d.ts.map +0 -1
- package/dist/storage/index.js.map +0 -7
- package/dist/storage/input-history-store.d.ts.map +0 -1
- package/dist/storage/memory-backend.d.ts.map +0 -1
- package/dist/storage/memory-consolidator.d.ts.map +0 -1
- package/dist/storage/memory-graph-backend.d.ts.map +0 -1
- package/dist/storage/plan-store.d.ts.map +0 -1
- package/dist/storage/plan-templates.d.ts.map +0 -1
- package/dist/storage/prompt-store.d.ts.map +0 -1
- package/dist/storage/prompt-usage-store.d.ts.map +0 -1
- package/dist/storage/provider-config-watcher.d.ts.map +0 -1
- package/dist/storage/queue-store.d.ts.map +0 -1
- package/dist/storage/recovery-lock.d.ts.map +0 -1
- package/dist/storage/replay-log-store.d.ts.map +0 -1
- package/dist/storage/session-analyzer.d.ts.map +0 -1
- package/dist/storage/session-checkpoint-cas.d.ts.map +0 -1
- package/dist/storage/session-event-bridge.d.ts.map +0 -1
- package/dist/storage/session-helpers.d.ts.map +0 -1
- package/dist/storage/session-id-resolver.d.ts.map +0 -1
- package/dist/storage/session-id.d.ts.map +0 -1
- package/dist/storage/session-read-scrubber.d.ts.map +0 -1
- package/dist/storage/session-reader.d.ts.map +0 -1
- package/dist/storage/session-recovery.d.ts.map +0 -1
- package/dist/storage/session-resume-validation.d.ts.map +0 -1
- package/dist/storage/session-rewind-apply.d.ts.map +0 -1
- package/dist/storage/session-rewinder.d.ts.map +0 -1
- package/dist/storage/session-store/delete-session-artifacts.d.ts.map +0 -1
- package/dist/storage/session-store/delete-session-guards.d.ts.map +0 -1
- package/dist/storage/session-store/directory-scan.d.ts.map +0 -1
- package/dist/storage/session-store/directory-session-files.d.ts.map +0 -1
- package/dist/storage/session-store/events.d.ts.map +0 -1
- package/dist/storage/session-store/fork-session.d.ts.map +0 -1
- package/dist/storage/session-store/index-reader.d.ts.map +0 -1
- package/dist/storage/session-store/load-cache.d.ts.map +0 -1
- package/dist/storage/session-store/load-session-data.d.ts.map +0 -1
- package/dist/storage/session-store/paths.d.ts.map +0 -1
- package/dist/storage/session-store/prune-helpers.d.ts.map +0 -1
- package/dist/storage/session-store/replay.d.ts.map +0 -1
- package/dist/storage/session-store/search-events.d.ts.map +0 -1
- package/dist/storage/session-store/shard-manifest.d.ts.map +0 -1
- package/dist/storage/session-store/summary-builder.d.ts.map +0 -1
- package/dist/storage/session-store/summary-header.d.ts.map +0 -1
- package/dist/storage/session-store/types.d.ts.map +0 -1
- package/dist/storage/session-store.d.ts.map +0 -1
- package/dist/storage/session-summary.d.ts.map +0 -1
- package/dist/storage/session-tool-call-ends.d.ts.map +0 -1
- package/dist/storage/session-writer-scrubber.d.ts.map +0 -1
- package/dist/storage/session-writer-truncate.d.ts.map +0 -1
- package/dist/storage/storage-concurrency.d.ts.map +0 -1
- package/dist/storage/task-store.d.ts.map +0 -1
- package/dist/storage/todos-checkpoint.d.ts.map +0 -1
- package/dist/storage/tool-audit-log.d.ts.map +0 -1
- package/dist/tasking/index.d.ts.map +0 -1
- package/dist/tasking/index.js.map +0 -7
- package/dist/tasking/task-store.d.ts.map +0 -1
- package/dist/tasking/task-tracker.d.ts.map +0 -1
- package/dist/tools/council-tool.d.ts.map +0 -1
- package/dist/tools/fallback-chain-manage-tool.d.ts.map +0 -1
- package/dist/tools/fallback-favorite-manage-tool.d.ts.map +0 -1
- package/dist/tools/fallback-manage-helpers.d.ts.map +0 -1
- package/dist/tools/fallback-manage-tool-options.d.ts.map +0 -1
- package/dist/tools/fallback-manage-tools.d.ts.map +0 -1
- package/dist/tools/fallback-model-ref-parse.d.ts.map +0 -1
- package/dist/tools/fallback-provider-key-store.d.ts.map +0 -1
- package/dist/tools/fallback-system-config-view-tool.d.ts.map +0 -1
- package/dist/tools/index.d.ts.map +0 -1
- package/dist/tools/index.js.map +0 -7
- package/dist/tools/mcp-control.d.ts.map +0 -1
- package/dist/tools/mcp-use.d.ts.map +0 -1
- package/dist/tools/one-shot-llm-tool.d.ts.map +0 -1
- package/dist/tools/plugin-manager.d.ts.map +0 -1
- package/dist/types/agent-bridge.d.ts.map +0 -1
- package/dist/types/attachment.d.ts.map +0 -1
- package/dist/types/autonomy.d.ts.map +0 -1
- package/dist/types/blocks.d.ts.map +0 -1
- package/dist/types/compactor.d.ts.map +0 -1
- package/dist/types/config/autonomy.d.ts.map +0 -1
- package/dist/types/config/context.d.ts.map +0 -1
- package/dist/types/config/fleet-chat.d.ts.map +0 -1
- package/dist/types/config/mcp-features.d.ts.map +0 -1
- package/dist/types/config/providers.d.ts.map +0 -1
- package/dist/types/config/root.d.ts.map +0 -1
- package/dist/types/config/runtime.d.ts.map +0 -1
- package/dist/types/config/skills-fleet-brain.d.ts.map +0 -1
- package/dist/types/config/tools.d.ts.map +0 -1
- package/dist/types/config.d.ts.map +0 -1
- package/dist/types/context-evidence.d.ts.map +0 -1
- package/dist/types/context-window.d.ts.map +0 -1
- package/dist/types/council.d.ts.map +0 -1
- package/dist/types/default-config.d.ts.map +0 -1
- package/dist/types/design-kit.d.ts.map +0 -1
- package/dist/types/error-handler.d.ts.map +0 -1
- package/dist/types/errors.d.ts.map +0 -1
- package/dist/types/file-event-record.d.ts.map +0 -1
- package/dist/types/hooks.d.ts.map +0 -1
- package/dist/types/index.d.ts.map +0 -1
- package/dist/types/index.js.map +0 -7
- package/dist/types/input-reader.d.ts.map +0 -1
- package/dist/types/logger.d.ts.map +0 -1
- package/dist/types/memory.d.ts.map +0 -1
- package/dist/types/messages.d.ts.map +0 -1
- package/dist/types/mode-prompts.d.ts.map +0 -1
- package/dist/types/mode.d.ts.map +0 -1
- package/dist/types/models-registry.d.ts.map +0 -1
- package/dist/types/multi-agent.d.ts.map +0 -1
- package/dist/types/observability.d.ts.map +0 -1
- package/dist/types/one-shot-llm.d.ts.map +0 -1
- package/dist/types/path-resolver.d.ts.map +0 -1
- package/dist/types/permission.d.ts.map +0 -1
- package/dist/types/plugin.d.ts.map +0 -1
- package/dist/types/prompt-registry.d.ts.map +0 -1
- package/dist/types/prompt.d.ts.map +0 -1
- package/dist/types/provider-runner.d.ts.map +0 -1
- package/dist/types/provider.d.ts.map +0 -1
- package/dist/types/quota-regex.d.ts.map +0 -1
- package/dist/types/renderer.d.ts.map +0 -1
- package/dist/types/retry-policy.d.ts.map +0 -1
- package/dist/types/secret-scrubber.d.ts.map +0 -1
- package/dist/types/secret-vault.d.ts.map +0 -1
- package/dist/types/selector.d.ts.map +0 -1
- package/dist/types/session-markers.d.ts.map +0 -1
- package/dist/types/session-markers.js.map +0 -7
- package/dist/types/session-reader.d.ts.map +0 -1
- package/dist/types/session-rewinder.d.ts.map +0 -1
- package/dist/types/session.d.ts.map +0 -1
- package/dist/types/side-effect.d.ts.map +0 -1
- package/dist/types/skill.d.ts.map +0 -1
- package/dist/types/slash-command.d.ts.map +0 -1
- package/dist/types/spec.d.ts.map +0 -1
- package/dist/types/system-prompt-contributor.d.ts.map +0 -1
- package/dist/types/system-prompt.d.ts.map +0 -1
- package/dist/types/task-graph.d.ts.map +0 -1
- package/dist/types/token-counter.d.ts.map +0 -1
- package/dist/types/tool-executor.d.ts.map +0 -1
- package/dist/types/tool-markers.d.ts.map +0 -1
- package/dist/types/tool.d.ts.map +0 -1
- package/dist/types/utility-types.d.ts.map +0 -1
- package/dist/utils/assert-never.d.ts.map +0 -1
- package/dist/utils/atomic-write.d.ts.map +0 -1
- package/dist/utils/cache-key.d.ts.map +0 -1
- package/dist/utils/child-env.d.ts.map +0 -1
- package/dist/utils/color.d.ts.map +0 -1
- package/dist/utils/compaction-preview.d.ts.map +0 -1
- package/dist/utils/config-backup.d.ts.map +0 -1
- package/dist/utils/config-json.d.ts.map +0 -1
- package/dist/utils/connectivity.d.ts.map +0 -1
- package/dist/utils/context-breakdown.d.ts.map +0 -1
- package/dist/utils/context-evidence.d.ts.map +0 -1
- package/dist/utils/continuous-memory-profiler.d.ts.map +0 -1
- package/dist/utils/crash-shield.d.ts.map +0 -1
- package/dist/utils/deep-merge.d.ts.map +0 -1
- package/dist/utils/diff.d.ts.map +0 -1
- package/dist/utils/error.d.ts.map +0 -1
- package/dist/utils/error.js.map +0 -7
- package/dist/utils/expect-defined.d.ts.map +0 -1
- package/dist/utils/expect-defined.js.map +0 -7
- package/dist/utils/glob-expand.d.ts.map +0 -1
- package/dist/utils/glob-match.d.ts.map +0 -1
- package/dist/utils/heap-watchdog-types.d.ts.map +0 -1
- package/dist/utils/heap-watchdog.d.ts.map +0 -1
- package/dist/utils/heap-watchdog.js.map +0 -7
- package/dist/utils/incoming-images.d.ts.map +0 -1
- package/dist/utils/index.d.ts.map +0 -1
- package/dist/utils/index.js.map +0 -7
- package/dist/utils/instruction-file.d.ts.map +0 -1
- package/dist/utils/ip-guard.d.ts.map +0 -1
- package/dist/utils/json-repair.d.ts.map +0 -1
- package/dist/utils/json-schema-validate.d.ts.map +0 -1
- package/dist/utils/lru-cache.d.ts.map +0 -1
- package/dist/utils/memory-flight-recorder.d.ts.map +0 -1
- package/dist/utils/merge-custom-models.d.ts.map +0 -1
- package/dist/utils/merge-models-payload.d.ts.map +0 -1
- package/dist/utils/message-invariants.d.ts.map +0 -1
- package/dist/utils/newline-normalize.d.ts.map +0 -1
- package/dist/utils/perf-profile.d.ts.map +0 -1
- package/dist/utils/pid.d.ts.map +0 -1
- package/dist/utils/project-identity.d.ts.map +0 -1
- package/dist/utils/project-watch.d.ts.map +0 -1
- package/dist/utils/regex-guard.d.ts.map +0 -1
- package/dist/utils/safe-json.d.ts.map +0 -1
- package/dist/utils/sage-output-block.d.ts.map +0 -1
- package/dist/utils/session-scoped-path.d.ts.map +0 -1
- package/dist/utils/sleep.d.ts.map +0 -1
- package/dist/utils/slug.d.ts.map +0 -1
- package/dist/utils/socket-path.d.ts.map +0 -1
- package/dist/utils/sqlite-warning.d.ts.map +0 -1
- package/dist/utils/string.d.ts.map +0 -1
- package/dist/utils/task-format.d.ts.map +0 -1
- package/dist/utils/term.d.ts.map +0 -1
- package/dist/utils/todos-format.d.ts.map +0 -1
- package/dist/utils/token-estimate.d.ts.map +0 -1
- package/dist/utils/tool-description-mode.d.ts.map +0 -1
- package/dist/utils/tool-name.d.ts.map +0 -1
- package/dist/utils/tool-output-serializer.d.ts.map +0 -1
- package/dist/utils/tool-result-render-mode.d.ts.map +0 -1
- package/dist/utils/tool-subject.d.ts.map +0 -1
- package/dist/utils/tool-wire-compact.d.ts.map +0 -1
- package/dist/utils/tree-kill.d.ts.map +0 -1
- package/dist/utils/tree-kill.js.map +0 -7
- package/dist/utils/ulid.d.ts.map +0 -1
- package/dist/utils/walk-ignore.d.ts.map +0 -1
- package/dist/utils/wstack-paths.d.ts.map +0 -1
- package/dist/worktree/index.d.ts.map +0 -1
- package/dist/worktree/index.js.map +0 -7
- package/dist/worktree/worktree-git.d.ts.map +0 -1
- package/dist/worktree/worktree-managed-ops.d.ts.map +0 -1
- package/dist/worktree/worktree-manager.d.ts.map +0 -1
- package/dist/worktree/worktree-types.d.ts.map +0 -1
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"version": 3,
|
|
3
|
-
"sources": ["../../src/chronicle/context.ts", "../../src/chronicle/identity.ts", "../../src/chronicle/file-observer.ts", "../../src/storage/storage-concurrency.ts", "../../src/utils/project-watch.ts", "../../src/utils/walk-ignore.ts", "../../src/chronicle/project-access.ts", "../../src/utils/wstack-paths.ts", "../../src/chronicle/journal.ts", "../../src/utils/atomic-write.ts", "../../src/types/errors.ts", "../../src/chronicle/event-hash.ts", "../../src/chronicle/partition-filename.ts", "../../src/chronicle/types.ts", "../../src/chronicle/metrics-store.ts", "../../src/utils/sqlite-warning.ts", "../../src/chronicle/query.ts", "../../src/chronicle/partition-range-cache.ts", "../../src/chronicle/legacy-journal-import.ts", "../../src/chronicle/sqlite-journal.ts", "../../src/chronicle/sqlite-query.ts", "../../src/chronicle/project-server-client.ts", "../../src/chronicle/project-server-endpoint.ts", "../../src/chronicle/project-server-protocol.ts", "../../src/chronicle/provider-adapter.ts", "../../src/chronicle/tool-adapter.ts", "../../src/chronicle/process-adapter.ts", "../../src/chronicle/health-monitor.ts", "../../src/chronicle/decision-adapter.ts", "../../src/chronicle/domain-adapter.ts", "../../src/chronicle/stream-adapter.ts", "../../src/chronicle/prompt-manifest.ts", "../../src/chronicle/review-adapter.ts", "../../src/chronicle/rollup-adapter.ts"],
|
|
4
|
-
"sourcesContent": ["import { randomUUID } from 'node:crypto';\nimport type { ChronicleCorrelation, ChronicleScope } from './types.js';\n\nexport interface ChronicleContext {\n scope: ChronicleScope;\n correlation: ChronicleCorrelation;\n}\n\n/** Create a root correlation context for a session, run, or background worker. */\nexport function createChronicleContext(\n scope: ChronicleScope,\n traceId: string = randomUUID(),\n): ChronicleContext {\n return {\n scope: { ...scope },\n correlation: { traceId, spanId: randomUUID() },\n };\n}\n\n/** Derive a child span without losing project/session/task attribution. */\nexport function childChronicleContext(\n parent: ChronicleContext,\n overrides: {\n scope?: Partial<ChronicleScope> | undefined;\n correlation?: Partial<Omit<ChronicleCorrelation, 'traceId'>> | undefined;\n } = {},\n): ChronicleContext {\n return {\n scope: { ...parent.scope, ...overrides.scope },\n correlation: {\n ...parent.correlation,\n ...overrides.correlation,\n traceId: parent.correlation.traceId,\n parentSpanId: parent.correlation.spanId,\n spanId: overrides.correlation?.spanId ?? randomUUID(),\n },\n };\n}\n", "import { createHash } from 'node:crypto';\nimport * as os from 'node:os';\nimport * as path from 'node:path';\n\nexport interface ChronicleRuntimeIdentityInput {\n globalRoot: string;\n projectId: string;\n projectDir: string;\n now?: Date | undefined;\n}\n\nexport interface ChronicleRuntimeLocation {\n installationId: string;\n machineId: string;\n projectId: string;\n /** Directory holding this project's Chronicle storage, whatever its format. */\n chronicleDirectory: string;\n /**\n * Day this location was resolved for, `YYYY-MM-DD` UTC.\n *\n * It is also the chain scope: the legacy writer used it to name a partition\n * file, and SQLite uses it as the `day` column. Exposing the day rather than\n * a `.jsonl` path keeps identity resolution independent of storage format.\n */\n day: string;\n}\n\n/**\n * Resolve privacy-preserving stable IDs and the UTC day that scopes a chain.\n * Raw host names and global paths never enter the journal envelope.\n */\nexport function resolveChronicleRuntimeLocation(\n input: ChronicleRuntimeIdentityInput,\n): ChronicleRuntimeLocation {\n const day = (input.now ?? new Date()).toISOString().slice(0, 10);\n return {\n installationId: stableId('installation', path.resolve(input.globalRoot)),\n machineId: stableId('machine', `${os.hostname()}\\0${os.platform()}\\0${os.arch()}`),\n projectId: input.projectId,\n chronicleDirectory: path.join(input.projectDir, 'chronicle'),\n day,\n };\n}\n\nfunction stableId(prefix: string, value: string): string {\n return `${prefix}_${createHash('sha256').update(value).digest('hex').slice(0, 24)}`;\n}\n", "import { createHash } from 'node:crypto';\nimport * as fsp from 'node:fs/promises';\nimport * as path from 'node:path';\nimport type { EventBus } from '../kernel/events.js';\nimport { mapWithConcurrency } from '../storage/storage-concurrency.js';\nimport { type ProjectWatchSubscription, watchProjectTree } from '../utils/project-watch.js';\nimport { DEFAULT_WALK_IGNORE_DIRS } from '../utils/walk-ignore.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\ninterface FileFingerprint {\n size: number;\n mtimeMs: number;\n hash?: string | undefined;\n}\n\ninterface RecentToolMutation {\n at: number;\n toolUseId: string;\n toolName: string;\n agentId?: string | undefined;\n sessionId?: string | undefined;\n}\n\nexport interface ChronicleToolMutationHint {\n path: string;\n toolUseId: string;\n toolName: string;\n agentId?: string | undefined;\n sessionId?: string | undefined;\n at?: number | undefined;\n}\n\nexport interface ChronicleFileObserverOptions {\n projectRoot: string;\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n events?: EventBus | undefined;\n debounceMs?: number | undefined;\n maxHashBytes?: number | undefined;\n excludedDirectories?: readonly string[] | undefined;\n /** Absolute or project-relative path prefixes that must never be observed. */\n excludedPaths?: readonly string[] | undefined;\n /** Min gap between full-project rescans triggered by null-filename events. */\n minFullRescanIntervalMs?: number | undefined;\n onError?: ((error: unknown) => void) | undefined;\n}\n\nexport interface ChronicleFileObserver {\n close(): Promise<void>;\n readonly watchedFiles: number;\n noteToolMutation(hint: ChronicleToolMutationHint): void;\n}\n\n/**\n * Directories this observer must never descend into.\n *\n * `.claude` earns its place the same way `.wrongstack` did: it is the tool's own\n * workspace, not the user's project, so nothing inside it is an \"external\n * mutation\" worth an audit event. It matters far more than it looks \u2014 git\n * worktrees live under `.claude/worktrees`, and a worktree is a full copy of the\n * repository. Creating one made the watcher report every tracked file as\n * `file.external.created`, and removing it reported every file again as\n * `deleted`. Measured on this repo: 85,619 of 85,813 file events in a single\n * day came from `.claude/worktrees`, ~95 MB of a 106 MB journal \u2014 90% of the\n * day's telemetry describing the tool watching itself.\n */\nconst DEFAULT_EXCLUDED = [\n ...DEFAULT_WALK_IGNORE_DIRS,\n '.wrongstack',\n '.claude',\n '.temp_files',\n];\nconst SCAN_HASH_CONCURRENCY = 32;\n// Platforms that omit the filename (common on Windows recursive watch) can\n// emit null-filename events in bursts. Each one used to trigger a full\n// project walk \u2014 bound rescans to this floor; a queued rescan is deferred,\n// never dropped, so no external mutation is lost.\nconst DEFAULT_FULL_RESCAN_MIN_INTERVAL_MS = 30_000;\n/** Max entries in recentToolMutations before oldest are evicted. */\nconst MAX_RECENT_TOOL_MUTATIONS = 500;\n\n/** Observe editor/user/external process mutations that bypass WrongStack tools. */\nexport async function startChronicleFileObserver(\n options: ChronicleFileObserverOptions,\n): Promise<ChronicleFileObserver> {\n const root = path.resolve(options.projectRoot);\n const excluded = new Set(options.excludedDirectories ?? DEFAULT_EXCLUDED);\n const excludedPaths = normalizeExcludedPaths(root, options.excludedPaths ?? []);\n const debounceMs = options.debounceMs ?? 120;\n const maxHashBytes = options.maxHashBytes ?? 8 * 1024 * 1024;\n const known = (await scanProject(root, excluded, excludedPaths, maxHashBytes, options.onError))\n .files;\n const recentToolMutations = new Map<string, RecentToolMutation>();\n const noteToolMutation = (hint: ChronicleToolMutationHint): void => {\n const absolute = path.isAbsolute(hint.path)\n ? path.normalize(hint.path)\n : path.resolve(root, hint.path);\n const relative = normalizeRelative(path.relative(root, absolute));\n if (relative.startsWith('../') || isExcluded(relative, excluded, excludedPaths)) return;\n recentToolMutations.set(relative, {\n at: hint.at ?? Date.now(),\n toolUseId: hint.toolUseId,\n toolName: hint.toolName,\n agentId: hint.agentId,\n sessionId: hint.sessionId,\n });\n // Evict oldest entries past the cap to prevent unbounded growth when\n // tool mutations accumulate faster than reconciliation drains them.\n if (recentToolMutations.size > MAX_RECENT_TOOL_MUTATIONS) {\n const overflow = recentToolMutations.size - MAX_RECENT_TOOL_MUTATIONS;\n const keys = [...recentToolMutations.keys()];\n for (let i = 0; i < overflow && i < keys.length; i++) {\n recentToolMutations.delete(keys[i]!);\n }\n }\n };\n const offToolProgress = options.events?.on('tool.progress', (event) => {\n if (event.event.type !== 'file_changed' || !event.event.path) return;\n noteToolMutation({\n path: event.event.path,\n toolUseId: event.id,\n toolName: event.name,\n agentId: event.agentId,\n sessionId: event.sessionId,\n });\n });\n const pending = new Set<string>();\n let timer: ReturnType<typeof setTimeout> | undefined;\n let closed = false;\n let flushTail: Promise<void> | null = null;\n const minFullRescanIntervalMs =\n options.minFullRescanIntervalMs ?? DEFAULT_FULL_RESCAN_MIN_INTERVAL_MS;\n // The startup scan just ran \u2014 the first watcher-triggered full rescan also\n // waits out the interval instead of immediately repeating that work.\n let lastFullScanAt = Date.now();\n let fullRescanTimer: ReturnType<typeof setTimeout> | undefined;\n\n const bumpDebounce = (): void => {\n if (timer) clearTimeout(timer);\n timer = setTimeout(() => {\n timer = undefined;\n drainPending();\n }, debounceMs);\n };\n\n // Some platforms omit the filename. A bounded full rescan recovers the\n // facts instead of silently losing an external mutation \u2014 but rescans walk\n // (and stat) the whole tree, so they are rate-limited: within the interval\n // the request is queued for the earliest allowed time, not dropped.\n const requestFullRescan = (): void => {\n if (closed) return;\n const since = Date.now() - lastFullScanAt;\n if (since >= minFullRescanIntervalMs) {\n pending.add('*');\n bumpDebounce();\n return;\n }\n if (fullRescanTimer) return;\n fullRescanTimer = setTimeout(() => {\n fullRescanTimer = undefined;\n if (closed) return;\n pending.add('*');\n bumpDebounce();\n }, minFullRescanIntervalMs - since);\n if (typeof fullRescanTimer.unref === 'function') fullRescanTimer.unref();\n };\n\n const schedule = (filename: string | Buffer | null): void => {\n if (closed) return;\n if (filename === null) {\n requestFullRescan();\n return;\n }\n const relative = normalizeRelative(String(filename));\n if (!relative || isExcluded(relative, excluded, excludedPaths)) return;\n pending.add(relative);\n bumpDebounce();\n };\n\n const reconcile = async (changedPaths: string[]): Promise<void> => {\n const wantsFullScan = changedPaths.includes('*');\n if (wantsFullScan) lastFullScanAt = Date.now();\n const fullScan = wantsFullScan\n ? await scanProject(root, excluded, excludedPaths, maxHashBytes, options.onError, known)\n : undefined;\n // Re-apply the exclusion boundary at reconciliation time. OS watchers can\n // report paths using a different recursive-root shape than the scheduling\n // callback (notably on Windows), and pending paths may outlive a directory\n // rename. Excluded tool workspaces must never become Chronicle events even\n // if an upstream watcher notification slips through the first filter.\n const candidates = (fullScan ? unionKeys(known, fullScan.files) : changedPaths).filter(\n (relative) => !isExcluded(relative, excluded, excludedPaths),\n );\n const changes: Array<{\n relative: string;\n before?: FileFingerprint | undefined;\n after?: FileFingerprint | undefined;\n }> = [];\n for (const relative of candidates) {\n const before = known.get(relative);\n // A successful full scan already paid the stat/read/hash cost. Reuse\n // those fingerprints instead of reading every file a second time.\n // When the scan is incomplete (a directory read or individual hash\n // threw), reuse whatever was hashed successfully and only re-probe\n // the files the scan did not reach \u2014 never treat a scan gap as a\n // deletion.\n const cached = fullScan?.files.get(relative);\n const after =\n cached ??\n (fullScan?.complete\n ? undefined\n : await fingerprint(path.join(root, relative), maxHashBytes));\n if (sameFingerprint(before, after)) continue;\n changes.push({ relative, before, after });\n }\n\n // Atomic saves and renames commonly arrive as delete+create. Matching the\n // last-known content hash preserves resource lineage when the OS provides\n // only generic \"rename\" notifications.\n const deleted = changes.filter((change) => change.before && !change.after);\n const created = changes.filter((change) => !change.before && change.after);\n const consumed = new Set<string>();\n const journalWrites: Promise<void>[] = [];\n for (const from of deleted) {\n const match = created.find(\n (to) =>\n !consumed.has(to.relative) &&\n from.before?.hash !== undefined &&\n from.before.hash === to.after?.hash,\n );\n if (!match) continue;\n consumed.add(from.relative);\n consumed.add(match.relative);\n known.delete(from.relative);\n known.set(match.relative, match.after!);\n journalWrites.push(\n recordMutation(\n options,\n 'file.external.renamed',\n match.relative,\n match.after,\n {\n operation: 'rename',\n previousPath: from.relative,\n previousResourceId: resourceId(from.relative),\n actor: 'external',\n },\n mutationAttribution(match.relative, recentToolMutations),\n ),\n );\n }\n\n for (const change of changes) {\n if (consumed.has(change.relative)) continue;\n if (!change.after) {\n known.delete(change.relative);\n journalWrites.push(\n recordMutation(\n options,\n 'file.external.deleted',\n change.relative,\n change.before,\n {\n operation: 'delete',\n actor: 'external',\n previousHash: change.before?.hash,\n previousSize: change.before?.size,\n },\n mutationAttribution(change.relative, recentToolMutations),\n ),\n );\n } else if (!change.before) {\n known.set(change.relative, change.after);\n journalWrites.push(\n recordMutation(\n options,\n 'file.external.created',\n change.relative,\n change.after,\n {\n operation: 'write',\n actor: 'external',\n },\n mutationAttribution(change.relative, recentToolMutations),\n ),\n );\n } else {\n known.set(change.relative, change.after);\n journalWrites.push(\n recordMutation(\n options,\n 'file.external.modified',\n change.relative,\n change.after,\n {\n operation: 'edit',\n actor: 'external',\n previousHash: change.before.hash,\n previousSize: change.before.size,\n },\n mutationAttribution(change.relative, recentToolMutations),\n ),\n );\n }\n }\n await Promise.all(journalWrites);\n };\n\n const drainPending = (): Promise<void> => {\n if (flushTail) return flushTail;\n const drain = (async () => {\n while (pending.size > 0) {\n const paths = [...pending];\n pending.clear();\n await reconcile(paths).catch((error) => options.onError?.(error));\n }\n })().finally(() => {\n if (flushTail === drain) flushTail = null;\n if (!closed && pending.size > 0) drainPending();\n });\n flushTail = drain;\n return drain;\n };\n\n let watcher: ProjectWatchSubscription;\n try {\n watcher = watchProjectTree(root, (event) => schedule(event.filename), {\n onError: (error) => options.onError?.(error),\n });\n } catch (error) {\n options.onError?.(error);\n throw error;\n }\n\n return {\n get watchedFiles() {\n return known.size;\n },\n noteToolMutation,\n async close() {\n if (closed) return;\n closed = true;\n offToolProgress?.();\n watcher.close();\n if (timer) {\n clearTimeout(timer);\n timer = undefined;\n }\n if (fullRescanTimer) {\n clearTimeout(fullRescanTimer);\n fullRescanTimer = undefined;\n }\n if (pending.size > 0) drainPending();\n await flushTail;\n recentToolMutations.clear();\n },\n };\n}\n\nasync function recordMutation(\n options: ChronicleFileObserverOptions,\n eventType: string,\n relativePath: string,\n state: FileFingerprint | undefined,\n attributes: Record<string, unknown>,\n attribution?: RecentToolMutation | undefined,\n): Promise<void> {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const operation = attributes['operation'] as 'write' | 'edit' | 'delete' | 'rename';\n options.events?.emit('file.activity', {\n filePath: path.join(options.projectRoot, relativePath),\n operation,\n phase: 'changed',\n source: attribution ? 'tool' : 'external',\n at: Date.now(),\n sessionId: context.scope.sessionId,\n traceId: context.correlation.traceId,\n agentId: attribution?.agentId ?? context.scope.agentId,\n ...(attribution ? { toolUseId: attribution.toolUseId, toolName: attribution.toolName } : {}),\n });\n const input: ChronicleEventInput = {\n eventType: attribution ? eventType.replace('.external.', '.tool.') : eventType,\n scope: {\n ...context.scope,\n ...(attribution?.sessionId ? { sessionId: attribution.sessionId } : {}),\n ...(attribution?.agentId ? { agentId: attribution.agentId } : {}),\n },\n correlation: {\n ...context.correlation,\n ...(attribution ? { toolCallId: attribution.toolUseId } : {}),\n },\n outcome: 'success',\n resource: {\n kind: 'file',\n id: resourceId(relativePath),\n path: normalizeRelative(relativePath),\n ...(state?.hash ? { contentHashAfter: state.hash } : {}),\n },\n attributes: {\n ...attributes,\n actor: attribution ? 'agent' : attributes['actor'],\n source: attribution ? 'tool' : 'external',\n toolName: attribution?.toolName,\n size: state?.size,\n mtimeMs: state?.mtimeMs,\n observedBy: 'fs.watch',\n },\n };\n await options.journal.append(input);\n}\n\nfunction mutationAttribution(\n relativePath: string,\n recent: Map<string, RecentToolMutation>,\n): RecentToolMutation | undefined {\n const value = recent.get(relativePath);\n if (!value) return undefined;\n recent.delete(relativePath);\n return Date.now() - value.at <= 2_000 ? value : undefined;\n}\n\nasync function scanProject(\n root: string,\n excluded: ReadonlySet<string>,\n excludedPaths: ReadonlySet<string>,\n maxHashBytes: number,\n onError?: ((error: unknown) => void) | undefined,\n previous?: ReadonlyMap<string, FileFingerprint> | undefined,\n): Promise<{ files: Map<string, FileFingerprint>; complete: boolean }> {\n const result = new Map<string, FileFingerprint>();\n const dirs = [''];\n let complete = true;\n while (dirs.length > 0) {\n const relativeDir = dirs.pop()!;\n try {\n const entries = await fsp.readdir(path.join(root, relativeDir), { withFileTypes: true });\n const filePaths: string[] = [];\n for (const entry of entries) {\n const relative = normalizeRelative(path.join(relativeDir, entry.name));\n if (isExcluded(relative, excluded, excludedPaths)) continue;\n if (entry.isDirectory()) {\n dirs.push(relative);\n } else if (entry.isFile()) {\n filePaths.push(relative);\n }\n }\n const fingerprints = await mapWithConcurrency(\n filePaths,\n SCAN_HASH_CONCURRENCY,\n async (relative): Promise<[string, FileFingerprint] | null> => {\n try {\n const value = await fingerprint(\n path.join(root, relative),\n maxHashBytes,\n previous?.get(relative),\n );\n return value ? [relative, value] : null;\n } catch (error) {\n complete = false;\n onError?.(error);\n return null;\n }\n },\n );\n for (const entry of fingerprints) {\n if (entry) result.set(entry[0], entry[1]);\n }\n } catch (error) {\n complete = false;\n onError?.(error);\n }\n }\n return { files: result, complete };\n}\n\nasync function fingerprint(\n filePath: string,\n maxHashBytes: number,\n previous?: FileFingerprint | undefined,\n): Promise<FileFingerprint | undefined> {\n try {\n const stat = await fsp.stat(filePath);\n if (!stat.isFile()) return undefined;\n const base: FileFingerprint = { size: stat.size, mtimeMs: stat.mtimeMs };\n // Unchanged size+mtime \u2192 reuse the known content hash instead of\n // re-reading the file. Full rescans over a quiet tree become stat-only.\n if (\n previous?.hash !== undefined &&\n previous.size === stat.size &&\n previous.mtimeMs === stat.mtimeMs\n ) {\n base.hash = previous.hash;\n return base;\n }\n if (stat.size <= maxHashBytes) {\n base.hash = createHash('sha256')\n .update(await fsp.readFile(filePath))\n .digest('hex');\n }\n return base;\n } catch (error) {\n if (typeof error === 'object' && error !== null && 'code' in error && error.code === 'ENOENT')\n return undefined;\n throw error;\n }\n}\n\nfunction sameFingerprint(a: FileFingerprint | undefined, b: FileFingerprint | undefined): boolean {\n if (!a || !b) return a === b;\n if (a.hash !== undefined && b.hash !== undefined) return a.hash === b.hash;\n return a.size === b.size && a.mtimeMs === b.mtimeMs;\n}\n\nfunction isExcluded(\n relative: string,\n excluded: ReadonlySet<string>,\n excludedPaths: ReadonlySet<string>,\n): boolean {\n const normalized = normalizeRelative(relative);\n if (normalized.split('/').some((segment) => excluded.has(segment))) return true;\n for (const prefix of excludedPaths) {\n if (normalized === prefix || normalized.startsWith(`${prefix}/`)) return true;\n }\n return false;\n}\n\nfunction normalizeExcludedPaths(root: string, values: readonly string[]): Set<string> {\n const result = new Set<string>();\n for (const value of values) {\n const relative = path.isAbsolute(value) ? path.relative(root, path.resolve(value)) : value;\n const normalized = normalizeRelative(relative).replace(/\\/+$/u, '');\n if (!normalized || normalized === '.' || normalized.startsWith('../')) continue;\n result.add(normalized);\n }\n return result;\n}\n\nfunction normalizeRelative(value: string): string {\n return value.replaceAll('\\\\', '/').replace(/^\\.\\//, '');\n}\n\nfunction resourceId(relativePath: string): string {\n return `file_${createHash('sha256').update(normalizeRelative(relativePath)).digest('hex').slice(0, 24)}`;\n}\n\nfunction unionKeys(a: ReadonlyMap<string, unknown>, b: ReadonlyMap<string, unknown>): string[] {\n return [...new Set([...a.keys(), ...b.keys()])];\n}\n", "export async function mapWithConcurrency<T, R>(\n items: readonly T[],\n concurrency: number,\n mapper: (item: T, index: number) => Promise<R>,\n): Promise<R[]> {\n if (items.length === 0) return [];\n const limit = Math.max(1, Math.floor(concurrency));\n const results = new Array<R>(items.length);\n let next = 0;\n\n async function worker(): Promise<void> {\n while (true) {\n const index = next;\n next++;\n if (index >= items.length) return;\n results[index] = await mapper(items[index] as T, index);\n }\n }\n\n const workers = Array.from({ length: Math.min(limit, items.length) }, () => worker());\n await Promise.all(workers);\n return results;\n}\n", "/**\n * Shared recursive project-tree watcher.\n *\n * Several subsystems each used to open their own `fs.watch(projectRoot,\n * {recursive:true})` \u2014 the codebase indexer, the chronicle file observer, and\n * the WebUI indexing mirror. Every recursive watch makes the OS track the\n * whole tree independently, so a single runtime paid that cost 2\u20133\u00D7. This\n * registry keeps ONE watcher per resolved root per process and fans events\n * out to all subscribers; the watcher closes when the last subscriber leaves.\n *\n * The registry lives behind a `Symbol.for` global so it stays a singleton\n * even if core is loaded twice (Windows path-casing double-load).\n *\n * @module utils/project-watch\n */\n\nimport * as fs from 'node:fs';\nimport * as path from 'node:path';\n\nexport interface ProjectWatchEvent {\n eventType: 'rename' | 'change';\n /** Path relative to the watched root as delivered by the OS, or null when omitted. */\n filename: string | null;\n}\n\nexport interface ProjectWatchSubscription {\n close(): void;\n}\n\ninterface Subscriber {\n listener: (event: ProjectWatchEvent) => void;\n onError?: ((error: unknown) => void) | undefined;\n}\n\ninterface WatchEntry {\n watcher: fs.FSWatcher;\n subscribers: Set<Subscriber>;\n /** Set once the underlying watcher errored or closed \u2014 dead entries are never reused. */\n dead: boolean;\n}\n\nconst REGISTRY_KEY = Symbol.for('wrongstack.projectWatchRegistry');\nconst globalScope = globalThis as { [REGISTRY_KEY]?: Map<string, WatchEntry> };\nif (!globalScope[REGISTRY_KEY]) globalScope[REGISTRY_KEY] = new Map();\nconst registry: Map<string, WatchEntry> = globalScope[REGISTRY_KEY];\n\nfunction registryKey(root: string): string {\n const resolved = path.resolve(root);\n return process.platform === 'win32' ? resolved.toLowerCase() : resolved;\n}\n\n/**\n * Subscribe to recursive change events under `root`, sharing one OS watcher\n * per root per process. Throws when the platform cannot create the watcher\n * (no recursive support, permission) and no live shared watcher exists \u2014\n * callers that can degrade should try/catch exactly as they would `fs.watch`.\n *\n * The watcher is non-persistent: it never keeps the process alive.\n */\nexport function watchProjectTree(\n root: string,\n listener: (event: ProjectWatchEvent) => void,\n opts?: { onError?: ((error: unknown) => void) | undefined },\n): ProjectWatchSubscription {\n const key = registryKey(root);\n let entry = registry.get(key);\n if (!entry || entry.dead) {\n const subscribers = new Set<Subscriber>();\n const watcher = fs.watch(\n path.resolve(root),\n { recursive: true, persistent: false },\n (eventType, filename) => {\n const event: ProjectWatchEvent = {\n eventType: eventType === 'rename' ? 'rename' : 'change',\n filename: filename === null ? null : String(filename),\n };\n for (const sub of subscribers) {\n try {\n sub.listener(event);\n } catch (error) {\n sub.onError?.(error);\n }\n }\n },\n );\n const created: WatchEntry = { watcher, subscribers, dead: false };\n const retire = (): void => {\n created.dead = true;\n if (registry.get(key) === created) registry.delete(key);\n };\n watcher.on('error', (error) => {\n // A watcher that errored is closed by Node \u2014 mark the entry dead so the\n // next acquire creates a fresh one instead of reusing a corpse.\n retire();\n for (const sub of subscribers) sub.onError?.(error);\n });\n // Watchers can also close without first emitting `error` (for example when\n // the watched tree disappears). Never leave that closed handle reusable.\n watcher.on('close', retire);\n registry.set(key, created);\n entry = created;\n }\n\n const active = entry;\n const subscriber: Subscriber = { listener, onError: opts?.onError };\n active.subscribers.add(subscriber);\n\n let closed = false;\n return {\n close() {\n if (closed) return;\n closed = true;\n active.subscribers.delete(subscriber);\n if (active.subscribers.size === 0 && !active.dead) {\n active.dead = true;\n if (registry.get(key) === active) registry.delete(key);\n try {\n active.watcher.close();\n } catch {\n /* already closed */\n }\n }\n },\n };\n}\n", "/**\n * Canonical directory-name ignore list for recursive tree walkers.\n *\n * Every walker that enumerates the project tree (glob, grep's native\n * fallback, tree, the codebase indexer, the chronicle file observer, the\n * semantic-search indexer, project fingerprinting, security scans) should\n * start from this list instead of hand-rolling its own \u2014 the hand-rolled\n * copies drifted, and a walker missing `.turbo` or `__pycache__` pays for\n * it by walking thousands of artifact files.\n *\n * The list is intentionally conservative: only dependency stores, VCS\n * internals, and build/cache artifacts that are never the subject of a\n * search. Directories a user may legitimately target (`.wrongstack`,\n * `vendor`, `out`) are NOT here \u2014 walkers with stricter needs append their\n * own entries.\n *\n * @module utils/walk-ignore\n */\n\n/** Directory basenames every recursive walker skips (matched per path segment). */\nexport const DEFAULT_WALK_IGNORE_DIRS: readonly string[] = Object.freeze([\n 'node_modules',\n '.git',\n 'dist',\n 'build',\n '.next',\n '.nuxt',\n '.turbo',\n 'coverage',\n '.nyc_output',\n '__snapshots__',\n '__pycache__',\n '.venv',\n 'venv',\n 'target',\n '.cache',\n '.parcel-cache',\n '.pnpm-store',\n '.gradle',\n]);\n\n/** Set form of {@link DEFAULT_WALK_IGNORE_DIRS} for per-segment membership checks. */\nexport const DEFAULT_WALK_IGNORE_SET: ReadonlySet<string> = new Set(DEFAULT_WALK_IGNORE_DIRS);\n", "import * as fsPromises from 'node:fs/promises';\nimport * as os from 'node:os';\nimport * as path from 'node:path';\nimport { resolveWstackPaths } from '../utils/wstack-paths.js';\nimport { type ChronicleRuntimeLocation, resolveChronicleRuntimeLocation } from './identity.js';\nimport { ChronicleJournal, type ChronicleJournalStats } from './journal.js';\nimport { ChronicleMetricsStore } from './metrics-store.js';\nimport { importLegacyChronicleJournal } from './legacy-journal-import.js';\nimport { ChronicleSqliteJournal } from './sqlite-journal.js';\nimport type { ChronicleSqliteQueryEngine } from './sqlite-query.js';\nimport {\n type ChronicleProjectServerCallOptions,\n ChronicleProjectServerClient,\n type ChronicleProjectServerClientOptions,\n ChronicleRemoteJournal,\n isChronicleProjectServerAvailable,\n resolveChronicleDaemonAvailability,\n} from './project-server-client.js';\nimport type {\n ChronicleProjectServerHealth,\n ChronicleServerOperationName,\n ChronicleServerOperations,\n} from './project-server-protocol.js';\nimport { CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION } from './project-server-protocol.js';\nimport { ChronicleQueryEngine } from './query.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEvent, ChronicleEventInput } from './types.js';\n\nexport interface ChronicleProjectAccessOptions {\n projectRoot: string;\n userHome?: string | undefined;\n retentionDays?: number | undefined;\n projectPaths?:\n | {\n globalRoot: string;\n projectId: string;\n projectDir: string;\n workspaceId: string;\n }\n | undefined;\n}\n\nexport interface ChronicleProjectAccess {\n readonly mode: 'server' | 'inline';\n call<O extends ChronicleServerOperationName>(\n op: O,\n args: ChronicleServerOperations[O]['args'],\n options?: ChronicleProjectServerCallOptions,\n ): Promise<ChronicleServerOperations[O]['result']>;\n close(): Promise<void>;\n}\n\nexport interface ChronicleEventJournalHandle {\n journal: ChronicleEventSink;\n identity: ChronicleRuntimeLocation;\n serverBacked: boolean;\n dispose(): Promise<void>;\n}\n\nexport function resolveChronicleProjectServerOptions(\n options: ChronicleProjectAccessOptions,\n): ChronicleProjectServerClientOptions {\n if (options.projectPaths) {\n return {\n projectRoot: path.resolve(options.projectRoot),\n ...options.projectPaths,\n ...(options.retentionDays !== undefined ? { retentionDays: options.retentionDays } : {}),\n };\n }\n const paths = resolveWstackPaths({\n projectRoot: options.projectRoot,\n userHome: options.userHome ?? os.homedir(),\n });\n return {\n projectRoot: path.resolve(options.projectRoot),\n globalRoot: paths.globalRoot,\n projectId: paths.projectHash,\n projectDir: paths.projectDir,\n workspaceId: paths.projectSlug,\n ...(options.retentionDays !== undefined ? { retentionDays: options.retentionDays } : {}),\n };\n}\n\n/**\n * Canonical read/process/control gateway for Chronicle consumers.\n *\n * Production builds use the per-project IPC owner. Explicit recovery mode\n * stays functional through the inline implementation; a missing daemon build\n * fails closed instead of silently creating a process-local journal.\n */\nexport function createChronicleProjectAccess(\n options: ChronicleProjectAccessOptions,\n): ChronicleProjectAccess {\n const resolved = resolveChronicleProjectServerOptions(options);\n if (isChronicleProjectServerAvailable()) {\n const client = new ChronicleProjectServerClient(resolved);\n return {\n mode: 'server',\n call: <O extends ChronicleServerOperationName>(\n op: O,\n args: ChronicleServerOperations[O]['args'],\n callOptions?: ChronicleProjectServerCallOptions,\n ) => client.call(op, args, callOptions),\n close: () => client.close(),\n };\n }\n assertInlineWasRequested('createChronicleProjectAccess');\n return new InlineChronicleProjectAccess(resolved);\n}\n\n/**\n * Refuse to run in-process unless the operator asked for it.\n *\n * Chronicle is a per-project singleton: one daemon owns the journal so every\n * terminal appends to the same hash chain. Dropping to an in-process journal\n * because the build could not be located gives each process its own chain\n * instead \u2014 no error, just silently divergent history. A missing build is a\n * defect to fix, not a mode to enter.\n */\nfunction assertInlineWasRequested(caller: string): void {\n if (resolveChronicleDaemonAvailability().kind !== 'missing-build') return;\n throw new Error(\n `${caller}: built Chronicle project server is unavailable. Build @wrongstack/core, ` +\n 'or set WRONGSTACK_CHRONICLE_INLINE=1 to explicitly accept a process-local journal.',\n );\n}\n\n/** Canonical producer sink selection used by CLI/TUI session wiring. */\nexport function createChronicleEventJournal(\n options: ChronicleProjectAccessOptions,\n): ChronicleEventJournalHandle {\n const resolved = resolveChronicleProjectServerOptions(options);\n const identity = resolveChronicleRuntimeLocation({\n globalRoot: resolved.globalRoot,\n projectId: resolved.projectId,\n projectDir: resolved.projectDir,\n });\n if (isChronicleProjectServerAvailable()) {\n const journal = new ChronicleRemoteJournal(resolved);\n return {\n journal,\n identity,\n serverBacked: true,\n dispose: () => journal.dispose(),\n };\n }\n assertInlineWasRequested('createChronicleEventJournal');\n if (useSqliteStore()) {\n const journal = new ChronicleSqliteEventSink(path.join(resolved.projectDir, 'chronicle'));\n return {\n journal,\n identity,\n serverBacked: false,\n dispose: () => journal.close(),\n };\n }\n const journal = new ChronicleJournal({\n filePath: legacyPartitionPath(identity),\n retentionDays: options.retentionDays,\n });\n return {\n journal,\n identity,\n serverBacked: false,\n dispose: () => journal.flush(),\n };\n}\n\n/** Compose the legacy partition path a `ChronicleJournal` writes to. */\nfunction legacyPartitionPath(location: { chronicleDirectory: string; day: string }): string {\n return path.join(location.chronicleDirectory, `${location.day}.events.jsonl`);\n}\n\n/**\n * Storage backend for the in-process path.\n *\n * SQLite is the default; `WRONGSTACK_CHRONICLE_STORE=jsonl` restores the legacy\n * partition writer. The escape hatch exists because the cut-over is the one\n * step of `chronicle-sqlite-journal-v1` that cannot be undone by re-reading the\n * old files \u2014 once events are appended to `chronicle.sqlite` they are not\n * mirrored back.\n */\nfunction useSqliteStore(): boolean {\n return process.env['WRONGSTACK_CHRONICLE_STORE'] !== 'jsonl';\n}\n\n/**\n * Producer sink over the SQLite journal.\n *\n * `createChronicleEventJournal` is synchronous but opening the store has to\n * import the legacy partitions first, so every append is queued behind that one\n * promise. Without the queue a session's first events could be written before\n * the import, landing *after* imported history in a chain that must stay dense.\n */\nclass ChronicleSqliteEventSink implements ChronicleEventSink {\n private readonly ready: Promise<ChronicleSqliteJournal>;\n private last: ChronicleJournalStats | undefined;\n\n constructor(directory: string) {\n this.ready = (async () => {\n await fsPromises.mkdir(directory, { recursive: true });\n const journal = new ChronicleSqliteJournal({ directory });\n try {\n await importLegacyChronicleJournal(journal, directory);\n } catch (error) {\n journal.close();\n throw error;\n }\n return journal;\n })();\n }\n\n async append(input: ChronicleEventInput): Promise<ChronicleEvent> {\n const journal = await this.ready;\n const event = await journal.append(input);\n this.last = journal.stats();\n return event;\n }\n\n async flush(): Promise<void> {\n await this.ready;\n }\n\n stats(): ChronicleJournalStats {\n return this.last ?? EMPTY_JOURNAL_STATS;\n }\n\n async close(): Promise<void> {\n (await this.ready).close();\n }\n}\n\nconst EMPTY_JOURNAL_STATS: ChronicleJournalStats = {\n acceptedEvents: 0,\n persistedEvents: 0,\n rejectedEvents: 0,\n failedEvents: 0,\n batches: 0,\n pendingEvents: 0,\n maxObservedPending: 0,\n largestBatch: 0,\n partitionRolls: 0,\n};\n\nclass InlineChronicleProjectAccess implements ChronicleProjectAccess {\n readonly mode = 'inline' as const;\n private readonly journals = new Map<string, ChronicleJournal>();\n private sqlite: Promise<ChronicleSqliteJournal> | undefined;\n\n constructor(private readonly options: ChronicleProjectServerClientOptions) {}\n\n /**\n * Open the SQLite journal, importing the legacy partitions the first time.\n *\n * The import is part of opening rather than a separate migration step so no\n * caller can read a half-migrated store: until it finishes, this promise has\n * not resolved and every operation is still queued behind it.\n */\n private store(): Promise<ChronicleSqliteJournal> {\n this.sqlite ??= (async () => {\n await fsPromises.mkdir(this.chronicleDirectory, { recursive: true });\n const journal = new ChronicleSqliteJournal({ directory: this.chronicleDirectory });\n try {\n await importLegacyChronicleJournal(journal, this.chronicleDirectory);\n } catch (error) {\n // Mirrors the daemon: a cached rejection would make every later call\n // fail identically while the handle holds the WAL open.\n this.sqlite = undefined;\n journal.close();\n throw error;\n }\n return journal;\n })();\n return this.sqlite;\n }\n\n async call<O extends ChronicleServerOperationName>(\n op: O,\n rawArgs: ChronicleServerOperations[O]['args'],\n _callOptions?: ChronicleProjectServerCallOptions,\n ): Promise<ChronicleServerOperations[O]['result']> {\n switch (op) {\n case 'ping':\n return this.health() as ChronicleServerOperations[O]['result'];\n case 'append': {\n const args = rawArgs as ChronicleServerOperations['append']['args'];\n if (useSqliteStore()) {\n const store = await this.store();\n return (await store.appendBatch(args.inputs)) as ChronicleServerOperations[O]['result'];\n }\n return (await Promise.all(\n args.inputs.map((input) => this.journalForToday().append(input)),\n )) as ChronicleServerOperations[O]['result'];\n }\n case 'flush':\n await this.flush();\n return undefined as ChronicleServerOperations[O]['result'];\n case 'purge': {\n const args = rawArgs as ChronicleServerOperations['purge']['args'];\n if (useSqliteStore()) {\n const store = await this.store();\n return (await store.purge(args)) as ChronicleServerOperations[O]['result'];\n }\n return (await this.journalForToday().purge(args)) as ChronicleServerOperations[O]['result'];\n }\n case 'query': {\n const args = rawArgs as ChronicleServerOperations['query']['args'];\n return (await (\n await this.queryEngine()\n ).query(args.query)) as ChronicleServerOperations[O]['result'];\n }\n case 'facet': {\n const args = rawArgs as ChronicleServerOperations['facet']['args'];\n const engine = await this.queryEngine();\n return {\n values: await engine.facet(args.field, args.query, args.limit),\n diagnostics: engine.diagnostics,\n } as ChronicleServerOperations[O]['result'];\n }\n case 'facets': {\n const args = rawArgs as ChronicleServerOperations['facets']['args'];\n const engine = await this.queryEngine();\n return {\n values: await engine.facets(args.fields, args.query, args.limit),\n diagnostics: engine.diagnostics,\n } as ChronicleServerOperations[O]['result'];\n }\n case 'graph': {\n const args = rawArgs as ChronicleServerOperations['graph']['args'];\n return (await (\n await this.queryEngine()\n ).graph(args.seed, args.hops, args.maxNodes)) as ChronicleServerOperations[O]['result'];\n }\n case 'metrics': {\n const args = rawArgs as ChronicleServerOperations['metrics']['args'];\n const store = ChronicleMetricsStore.open(this.chronicleDirectory);\n try {\n const refreshed = args.refresh === false\n ? { ingestedEvents: 0, ingestedBytes: 0, sourceFiles: 0, invalidLines: 0 }\n : await store.refresh();\n const data =\n args.view === 'providers'\n ? store.providerDaily(args.providers)\n : args.view === 'tasks'\n ? store.taskOutcomes(args.tasks)\n : args.view === 'files'\n ? store.fileLineage(args.files)\n : store.summary();\n return { refreshed, data } as ChronicleServerOperations[O]['result'];\n } finally {\n store.close();\n }\n }\n }\n }\n\n async close(): Promise<void> {\n await this.flush();\n // Releasing the SQLite handle is part of closing, not an optimization: the\n // connection holds `-wal` and `-shm` sidecars open, so leaving it dangling\n // leaks a file handle per access object and blocks directory removal.\n if (this.sqlite) {\n const store = await this.sqlite;\n this.sqlite = undefined;\n store.close();\n }\n }\n\n private get chronicleDirectory(): string {\n return path.join(this.options.projectDir, 'chronicle');\n }\n\n private journalForToday(): ChronicleJournal {\n const now = new Date();\n const day = now.toISOString().slice(0, 10);\n let journal = this.journals.get(day);\n if (!journal) {\n const identity = resolveChronicleRuntimeLocation({\n globalRoot: this.options.globalRoot,\n projectId: this.options.projectId,\n projectDir: this.options.projectDir,\n now,\n });\n journal = new ChronicleJournal({\n filePath: legacyPartitionPath(identity),\n retentionDays: this.options.retentionDays,\n });\n this.journals.set(day, journal);\n }\n return journal;\n }\n\n /**\n * Both engines expose the same read surface, so every `call()` branch is\n * backend-agnostic. The SQLite one shares the journal's connection, which is\n * also what makes the legacy import a precondition of reading.\n */\n private async queryEngine(): Promise<ChronicleQueryEngine | ChronicleSqliteQueryEngine> {\n if (useSqliteStore()) return (await this.store()).queryEngine();\n return ChronicleQueryEngine.fromDirectory(this.chronicleDirectory);\n }\n\n private async flush(): Promise<void> {\n if (useSqliteStore()) {\n // Writes are transactional, so this only has to wait for an in-flight\n // open (and its legacy import) rather than drain a buffer.\n if (this.sqlite) await this.sqlite;\n return;\n }\n await Promise.all([...this.journals.values()].map((journal) => journal.flush()));\n }\n\n private health(): ChronicleProjectServerHealth {\n const memory = process.memoryUsage();\n return {\n protocolVersion: CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION,\n pid: process.pid,\n projectRoot: this.options.projectRoot,\n projectDir: this.options.projectDir,\n chronicleDirectory: this.chronicleDirectory,\n endpoint: 'inline',\n startedAt: new Date(Date.now() - process.uptime() * 1_000).toISOString(),\n checkedAt: Date.now(),\n uptimeMs: Math.round(process.uptime() * 1_000),\n clients: 1,\n activeRequests: 0,\n journal: this.journalForToday().stats(),\n watcher: { active: false, watchedFiles: 0 },\n memory: {\n rss: memory.rss,\n heapUsed: memory.heapUsed,\n heapTotal: memory.heapTotal,\n external: memory.external,\n },\n };\n }\n}\n", "import { createHash } from 'node:crypto';\nimport * as fs from 'node:fs';\nimport * as os from 'node:os';\nimport * as path from 'node:path';\n\n/**\n * Path layout. All developer-level state lives in ~/.wrongstack/.\n * Per-project state is keyed by the canonical project root under\n * ~/.wrongstack/projects/<slug>/. Linked Git worktrees resolve to their main\n * checkout so coordination and durable state are shared across worktrees.\n *\n * The ONLY thing inside the project tree is the optional\n * .wrongstack/AGENTS.md (committed) and .wrongstack/skills/ (committed).\n */\n\nexport interface WstackPaths {\n /** ~/.wrongstack \u2014 global root. */\n globalRoot: string;\n /** Active profile name resolved from the bootstrap config. */\n profileName: string;\n /** ~/.wrongstack/profiles/<activeProfile> \u2014 active user-profile root. */\n profileDir: string;\n /** Absolute project root. */\n projectRoot: string;\n /** Home directory (~) \u2014 base for foreign tool state (~/.codex, ~/.agents, \u2026). */\n homeDir: string;\n /**\n * ~/.wrongstack/profiles/<activeProfile> \u2014 directory for profile-scoped\n * user state (mode.json, statusline.json, custom-context-modes.json, \u2026).\n */\n configDir: string;\n /** ~/.wrongstack/config.json \u2014 bootstrap config (activeProfile + version). */\n globalConfig: string;\n /**\n * ~/.wrongstack/profiles \u2014 directory containing per-profile configs.\n * Each profile has its own subdirectory with a config.json.\n */\n profilesDir: string;\n /**\n * Resolve the config path for a named profile.\n * Returns ~/.wrongstack/profiles/<name>/config.json.\n */\n profileConfig: (name: string) => string;\n /** Resolve ~/.wrongstack/profiles/<name>/statusline.json */\n profileStatuslineConfig: (name: string) => string;\n /** Resolve ~/.wrongstack/profiles/<name>/mode.json */\n profileModeConfig: (name: string) => string;\n /** Resolve ~/.wrongstack/profiles/<name>/provider-status.json */\n profileProviderStatus: (name: string) => string;\n /** Resolve ~/.wrongstack/profiles/<name>/update-cache.json */\n profileUpdateCache: (name: string) => string;\n /** ~/.wrongstack/.key \u2014 32 random bytes, mode 0600, AES-GCM key for the secret vault. */\n secretsKey: string;\n /** ~/.wrongstack/profiles/<activeProfile>/memory.md \u2014 profile memory. */\n globalMemory: string;\n /** ~/.wrongstack/profiles/<activeProfile>/skills \u2014 profile skills. */\n globalSkills: string;\n /** ~/.claude/skills \u2014 user-global skills from foreign coding agents (Claude Code, Codex, \u2026). Read-only. */\n globalClaudeSkills: string;\n /** ~/.wrongstack/profiles/<activeProfile>/design-kits \u2014 profile Design Studio kits. */\n globalDesignKits: string;\n /** ~/.wrongstack/profiles/<activeProfile>/prompts \u2014 profile prompt library. */\n globalPrompts: string;\n /** ~/.wrongstack/profiles/<activeProfile>/instructions \u2014 profile instruction overrides. */\n globalInstructions: string;\n /** ~/.wrongstack/profiles/<activeProfile>/prompt-usage.json \u2014 prompt usage. */\n promptUsage: string;\n /** ~/.wrongstack/cache \u2014 fetched data (models.dev, etc.). */\n cacheDir: string;\n /** ~/.wrongstack/cache/models.dev.json */\n modelsCache: string;\n /** ~/.wrongstack/cache/models-overlay.json \u2014 cached curated overlay. */\n modelsOverlayCache: string;\n /**\n * Per-project codebase symbol index (SQLite). Lives under the global project\n * dir \u2014 NOT inside the repo \u2014 so it never clutters the working tree or needs\n * gitignoring. `~/.wrongstack/projects/<hash>/codebase-index`.\n */\n projectCodebaseIndex: string;\n /** ~/.wrongstack/profiles/<activeProfile>/history \u2014 REPL line history. */\n historyFile: string;\n /** ~/.wrongstack/logs/wrongstack.log */\n logFile: string;\n /** ~/.wrongstack/projects/<hash> */\n projectDir: string;\n /** ~/.wrongstack/projects/<hash>/memory.md */\n projectMemory: string;\n /** ~/.wrongstack/projects/<hash>/sessions */\n projectSessions: string;\n /** ~/.wrongstack/projects/<hash>/trust.json */\n projectTrust: string;\n /** ~/.wrongstack/projects/<hash>/meta.json */\n projectMeta: string;\n /** ~/.wrongstack/projects/<hash>/config.local.json \u2014 optional override */\n projectLocalConfig: string;\n /** <project>/.wrongstack/config.json \u2014 per-project settings (safe fields only).\n * This lives inside the project root so it can be gitignored or shared. */\n inProjectConfig: string;\n /** <project>/.wrongstack/AGENTS.md \u2014 committed project memory. */\n inProjectAgentsFile: string;\n /** <project>/.wrongstack/skills \u2014 committed project skills. */\n inProjectSkills: string;\n /** <project>/.claude/skills \u2014 project skills authored for foreign coding agents (Claude Code, \u2026). Read-only. */\n inProjectClaudeSkills: string;\n /** <project>/.wrongstack/prompts \u2014 committed project prompt library. */\n inProjectPrompts: string;\n /** <project>/.wrongstack/instructions \u2014 committed project instruction overrides. */\n inProjectInstructions: string;\n /** <project>/.wrongstack/design-kits \u2014 committed project Design Studio kits. */\n inProjectDesignKits: string;\n /** <project>/.wrongstack/worktrees \u2014 git worktrees for per-phase isolation (gitignored). */\n inProjectWorktrees: string;\n /** Stable hash for the canonical project root (shared by linked Git worktrees). */\n projectHash: string;\n /** Human-readable canonical project slug, shared by linked Git worktrees. */\n projectSlug: string;\n /** ~/.wrongstack/projects/<hash>/goal.json \u2014 goal persistence */\n projectGoal: string;\n /** ~/.wrongstack/projects/<hash>/input-history.json \u2014 TUI prompt input history */\n projectInputHistory: string;\n /** ~/.wrongstack/projects/<hash>/specs \u2014 SDD spec files */\n projectSpecs: string;\n /** ~/.wrongstack/projects/<hash>/task-graphs \u2014 SDD task graphs */\n projectTaskGraphs: string;\n /** ~/.wrongstack/projects/<hash>/sdd-session.json \u2014 SDD session state */\n projectSddSession: string;\n /** ~/.wrongstack/projects/<hash>/plan.json \u2014 plan persistence */\n projectPlan: string;\n /** ~/.wrongstack/projects/<hash>/autophase \u2014 Goal phase-graph JSON files (dir name kept for backward compat) */\n projectAutophase: string;\n /** ~/.wrongstack/projects/<hash>/sdd-boards \u2014 live SDD board snapshots + JSONL event logs */\n projectSddBoards: string;\n /** ~/.wrongstack/profiles/<activeProfile>/sync.json \u2014 CloudSync configuration */\n syncConfig: string;\n /** ~/.wrongstack/config-history \u2014 timestamped backups on every config write */\n configHistoryDir: string;\n /** Function to get the status.json path for a project given its hash. */\n projectStatus: (projectHash: string) => string;\n}\n\n/**\n * Resolve the stable project identity root used by global WrongStack state.\n *\n * A linked Git worktree has its own checkout path and a `.git` *file* that\n * points into `<main>/.git/worktrees/<name>`. Its `commondir` points back to\n * the main checkout's `.git` directory. Treating the linked checkout path as\n * the project identity would split one repository into multiple session,\n * registry, and mailbox directories \u2014 agents in different worktrees would be\n * unable to see or message each other.\n *\n * Project-local paths still use the caller's actual checkout. Only global\n * state identity is canonicalized. Non-Git projects, normal checkouts, Git\n * submodules, and separate-git-dir layouts keep their existing identity.\n */\nexport function canonicalProjectRoot(absRoot: string): string {\n const checkoutRoot = path.resolve(absRoot);\n const dotGit = path.join(checkoutRoot, '.git');\n\n try {\n if (!fs.statSync(dotGit).isFile()) return checkoutRoot;\n\n const gitDirLine = fs.readFileSync(dotGit, 'utf8').trim();\n const match = /^gitdir:\\s*(.+)$/i.exec(gitDirLine);\n if (!match?.[1]) return checkoutRoot;\n\n const gitDir = path.resolve(checkoutRoot, match[1].trim());\n const commonDirFile = path.join(gitDir, 'commondir');\n if (!fs.statSync(commonDirFile).isFile()) return checkoutRoot;\n\n const commonDir = path.resolve(gitDir, fs.readFileSync(commonDirFile, 'utf8').trim());\n // Linked worktrees created by Git share the main checkout's `.git` dir.\n // A submodule or --separate-git-dir layout may point elsewhere; do not\n // guess a working-tree root for those shapes.\n if (path.basename(commonDir).toLowerCase() !== '.git') return checkoutRoot;\n return path.dirname(commonDir);\n } catch {\n // Missing/malformed administrative files must never make path resolution\n // fail. Falling back preserves the pre-canonicalization behavior.\n return checkoutRoot;\n }\n}\n\nexport function projectHash(absRoot: string): string {\n return createHash('sha256').update(canonicalProjectRoot(absRoot)).digest('hex').slice(0, 12);\n}\n\n/**\n * Human-readable project directory name: slugified folder name + short hash\n * suffix for uniqueness. e.g. `wrongstack-a1b2c3` instead of `3024e5e6fa58`.\n */\nexport function projectSlug(absRoot: string): string {\n const identityRoot = canonicalProjectRoot(absRoot);\n const base = slugify(path.basename(identityRoot));\n const hash = createHash('sha256').update(identityRoot).digest('hex').slice(0, 6);\n return `${base}-${hash}`;\n}\n\n/** Turn a folder name into a filesystem-safe lowercase slug. */\nfunction slugify(name: string): string {\n return (\n name\n .toLowerCase()\n // Collapse any run of non-alphanumeric chars into a single hyphen.\n .replace(/[^a-z0-9]+/g, '-')\n .replace(/^-+|-+$/g, '')\n .slice(0, 40) || 'project'\n );\n}\n\nexport interface WstackPathOptions {\n userHome?: string | undefined;\n projectRoot: string;\n /** Override the global root (e.g. for tests). Default: `${userHome}/.wrongstack`. */\n globalRoot?: string | undefined;\n /** Explicit profile override. Otherwise read from the root bootstrap config. */\n profileName?: string | undefined;\n}\n\n/** Make an untrusted profile name safe for use as one path segment. */\nexport function safeProfileName(name: string | undefined): string {\n const safe = (name ?? '').replace(/[/\\\\:]/g, '_').replace(/\\.\\./g, '_').trim();\n return safe || 'default';\n}\n\n/**\n * Resolve the selected profile from ~/.wrongstack/config.json. The root file\n * is bootstrap metadata only; a missing/corrupt bootstrap selects `default`.\n */\nexport function activeProfileName(globalRoot: string): string {\n try {\n const parsed = JSON.parse(fs.readFileSync(path.join(globalRoot, 'config.json'), 'utf8')) as {\n activeProfile?: unknown;\n };\n return safeProfileName(typeof parsed.activeProfile === 'string' ? parsed.activeProfile : undefined);\n } catch {\n return 'default';\n }\n}\n\n/**\n * The global `~/.wrongstack` root, honoring the `WRONGSTACK_HOME` env\n * override. The override exists so tests (and sandboxed runs) can redirect\n * ALL global state \u2014 config, secrets, logs, projects/, mailboxes \u2014 away from\n * the real user home. Before it existed, `pnpm test` booted runtimes against\n * the real `~/.wrongstack`: it read the user's real config.json (starting a\n * second live Telegram poller), appended to the real wrongstack.log, and left\n * ~20k orphaned fixture dirs under projects/.\n *\n * Every code path that wants the global dir must come through here (or\n * through `resolveWstackPaths`) instead of `path.join(os.homedir(), '.wrongstack')`.\n */\nexport function wstackGlobalRoot(): string {\n const fromEnv = process.env['WRONGSTACK_HOME'];\n if (fromEnv && fromEnv.trim().length > 0) return path.resolve(fromEnv);\n return path.join(os.homedir(), '.wrongstack');\n}\n\nexport function resolveWstackPaths(opts: WstackPathOptions): WstackPaths {\n // Precedence: explicit globalRoot > explicit userHome (callers/tests that\n // pass one expect paths under it) > WRONGSTACK_HOME env > real home dir.\n const globalRoot =\n opts.globalRoot ?? (opts.userHome ? path.join(opts.userHome, '.wrongstack') : wstackGlobalRoot());\n // Home dir for FOREIGN tool state (Claude Code's ~/.claude). Independent of\n // WRONGSTACK_HOME, which redirects only WrongStack state: a real user's\n // Claude skills live in their real home, but tests pass `userHome` to keep\n // both `.wrongstack` and `.claude` under a temp dir.\n const homeDir = opts.userHome ?? os.homedir();\n const profileName = safeProfileName(opts.profileName ?? activeProfileName(globalRoot));\n const profileDir = path.join(globalRoot, 'profiles', profileName);\n const hash = projectHash(opts.projectRoot);\n const slug = projectSlug(opts.projectRoot);\n const projectDir = path.join(globalRoot, 'projects', slug);\n return {\n globalRoot,\n profileName,\n profileDir,\n projectRoot: opts.projectRoot,\n homeDir,\n configDir: profileDir,\n globalConfig: path.join(globalRoot, 'config.json'),\n profilesDir: path.join(globalRoot, 'profiles'),\n profileConfig: (name: string) => {\n return path.join(globalRoot, 'profiles', safeProfileName(name), 'config.json');\n },\n profileStatuslineConfig: (name: string) => {\n return path.join(globalRoot, 'profiles', safeProfileName(name), 'statusline.json');\n },\n profileModeConfig: (name: string) => {\n return path.join(globalRoot, 'profiles', safeProfileName(name), 'mode.json');\n },\n profileProviderStatus: (name: string) => {\n return path.join(globalRoot, 'profiles', safeProfileName(name), 'provider-status.json');\n },\n profileUpdateCache: (name: string) => {\n return path.join(globalRoot, 'profiles', safeProfileName(name), 'update-cache.json');\n },\n secretsKey: path.join(globalRoot, '.key'),\n globalMemory: path.join(profileDir, 'memory.md'),\n globalSkills: path.join(profileDir, 'skills'),\n globalClaudeSkills: path.join(homeDir, '.claude', 'skills'),\n globalDesignKits: path.join(profileDir, 'design-kits'),\n globalPrompts: path.join(profileDir, 'prompts'),\n globalInstructions: path.join(profileDir, 'instructions'),\n promptUsage: path.join(profileDir, 'prompt-usage.json'),\n cacheDir: path.join(globalRoot, 'cache'),\n modelsCache: path.join(globalRoot, 'cache', 'models.dev.json'),\n modelsOverlayCache: path.join(globalRoot, 'cache', 'models-overlay.json'),\n historyFile: path.join(profileDir, 'history'),\n logFile: path.join(globalRoot, 'logs', 'wrongstack.log'),\n projectDir,\n projectCodebaseIndex: path.join(projectDir, 'codebase-index'),\n projectMemory: path.join(projectDir, 'memory.md'),\n projectSessions: path.join(projectDir, 'sessions'),\n projectTrust: path.join(projectDir, 'trust.json'),\n projectMeta: path.join(projectDir, 'meta.json'),\n projectLocalConfig: path.join(projectDir, 'config.local.json'),\n inProjectConfig: path.join(opts.projectRoot, '.wrongstack', 'config.json'),\n inProjectAgentsFile: path.join(opts.projectRoot, '.wrongstack', 'AGENTS.md'),\n inProjectSkills: path.join(opts.projectRoot, '.wrongstack', 'skills'),\n inProjectClaudeSkills: path.join(opts.projectRoot, '.claude', 'skills'),\n inProjectPrompts: path.join(opts.projectRoot, '.wrongstack', 'prompts'),\n inProjectInstructions: path.join(opts.projectRoot, '.wrongstack', 'instructions'),\n inProjectDesignKits: path.join(opts.projectRoot, '.wrongstack', 'design-kits'),\n inProjectWorktrees: path.join(opts.projectRoot, '.wrongstack', 'worktrees'),\n projectHash: hash,\n projectSlug: slug,\n projectGoal: path.join(projectDir, 'goal.json'),\n projectInputHistory: path.join(projectDir, 'input-history.json'),\n projectSpecs: path.join(projectDir, 'specs'),\n projectTaskGraphs: path.join(projectDir, 'task-graphs'),\n projectSddSession: path.join(projectDir, 'sdd-session.json'),\n projectPlan: path.join(projectDir, 'plan.json'),\n projectAutophase: path.join(projectDir, 'autophase'),\n projectSddBoards: path.join(projectDir, 'sdd-boards'),\n syncConfig: path.join(profileDir, 'sync.json'),\n configHistoryDir: path.join(globalRoot, 'config-history'),\n projectStatus: (projectHash: string) => path.join(globalRoot, 'projects', projectHash, 'status.json'),\n };\n}\n", "import { randomUUID } from 'node:crypto';\nimport { createReadStream } from 'node:fs';\nimport * as fs from 'node:fs/promises';\nimport * as path from 'node:path';\nimport { createInterface } from 'node:readline';\nimport { atomicWrite, withFileLock } from '../utils/atomic-write.js';\nimport { GENESIS_HASH, hashValue } from './event-hash.js';\nimport { comparePartitionPaths } from './partition-filename.js';\nimport {\n CHRONICLE_SCHEMA_VERSION,\n type ChronicleEvent,\n type ChronicleEventInput,\n type ChronicleVerifyResult,\n} from './types.js';\n\nconst DEFAULT_MAX_PARTITION_BYTES = 100 * 1024 * 1024;\nconst DEFAULT_ROTATION_WINDOW_MS = 60 * 60 * 1000;\nconst RETENTION_CHECKPOINT_VERSION = 1;\n\nexport interface ChronicleRetentionCheckpoint {\n version: typeof RETENTION_CHECKPOINT_VERSION;\n sequence: number;\n hash: string;\n}\n\nexport interface ChronicleJournalOptions {\n filePath: string;\n now?: (() => Date) | undefined;\n monotonicNow?: (() => bigint) | undefined;\n idFactory?: (() => string) | undefined;\n maxPending?: number | undefined;\n batchWindowMs?: number | undefined;\n maxPartitionSizeBytes?: number | undefined;\n rotationWindowMs?: number | undefined;\n retentionDays?: number | undefined;\n autoPurgeIntervalMs?: number | undefined;\n}\nexport interface ChronicleJournalStats {\n acceptedEvents: number; persistedEvents: number; rejectedEvents: number; failedEvents: number;\n batches: number; pendingEvents: number; maxObservedPending: number; largestBatch: number;\n lastBatchDurationMs?: number | undefined;\n partitionRolls: number;\n}\nexport interface ChroniclePurgeOptions {\n retentionDays: number;\n dryRun?: boolean | undefined;\n files?: string[] | undefined;\n}\nexport interface ChroniclePurgeResult {\n deletedCount: number;\n deletedBytes: number;\n skippedCount: number;\n errors: Array<{ file: string; reason: string }>;\n candidates?: string[] | undefined;\n}\n\nexport class ChronicleJournal {\n private readonly basePath: string;\n private readonly now: () => Date;\n private readonly monotonicNow: () => bigint;\n private readonly idFactory: () => string;\n private readonly maxPending: number;\n private readonly batchWindowMs: number;\n private readonly maxPartitionSizeBytes: number;\n private readonly rotationWindowMs: number;\n private readonly retentionDays: number;\n private readonly autoPurgeIntervalMs: number;\n private pending: Array<{ input: ChronicleEventInput; resolve: (event: ChronicleEvent) => void; reject: (error: unknown) => void; }> = [];\n private drainPromise: Promise<void> | undefined;\n private drainScheduled = false;\n private drainTimer: ReturnType<typeof setTimeout> | undefined;\n private readonly counters = { acceptedEvents: 0, persistedEvents: 0, rejectedEvents: 0, failedEvents: 0, batches: 0, maxObservedPending: 0, largestBatch: 0, partitionRolls: 0 };\n private lastBatchDurationMs: number | undefined;\n private partitionIndex = 0;\n private partitionStartedAt: number;\n private partitionSizeBytes = 0;\n private stateInitialized = false;\n private lastSequence = 0;\n private lastHash: string = GENESIS_HASH;\n private lastAutoPurgeAt = 0;\n\n constructor(options: ChronicleJournalOptions) {\n this.basePath = path.resolve(options.filePath);\n this.now = options.now ?? (() => new Date());\n this.monotonicNow = options.monotonicNow ?? (() => process.hrtime.bigint());\n this.idFactory = options.idFactory ?? randomUUID;\n this.maxPending = Math.max(1, options.maxPending ?? 100_000);\n this.batchWindowMs = Math.max(0, options.batchWindowMs ?? 5);\n this.maxPartitionSizeBytes = options.maxPartitionSizeBytes ?? DEFAULT_MAX_PARTITION_BYTES;\n this.rotationWindowMs = options.rotationWindowMs ?? DEFAULT_ROTATION_WINDOW_MS;\n this.retentionDays = options.retentionDays && Number.isFinite(options.retentionDays) && options.retentionDays > 0 ? options.retentionDays : 0;\n this.autoPurgeIntervalMs = Math.max(0, options.autoPurgeIntervalMs ?? 3_600_000);\n this.partitionStartedAt = Date.now();\n }\n\n get path(): string { return this.partitionIndex === 0 ? this.basePath : rotatedPath(this.basePath, this.partitionIndex); }\n\n stats(): ChronicleJournalStats {\n return { ...this.counters, pendingEvents: this.pending.length, ...(this.lastBatchDurationMs !== undefined ? { lastBatchDurationMs: this.lastBatchDurationMs } : {}) };\n }\n\n append(input: ChronicleEventInput): Promise<ChronicleEvent> {\n if (this.pending.length >= this.maxPending) { this.counters.rejectedEvents++; return Promise.reject(new Error(`Chronicle backpressure limit reached (${this.maxPending} pending events)`)); }\n const promise = new Promise<ChronicleEvent>((resolve, reject) => { this.pending.push({ input, resolve, reject }); });\n this.counters.acceptedEvents++;\n this.counters.maxObservedPending = Math.max(this.counters.maxObservedPending, this.pending.length);\n this.scheduleDrain();\n return promise;\n }\n\n async readAll(): Promise<ChronicleEvent[]> {\n await this.flush();\n const files = await collectPartitions(this.basePath);\n const entries: ChronicleEvent[] = [];\n for (const file of files) entries.push(...(await readEntriesStrict(file)));\n return entries;\n }\n\n async flush(): Promise<void> {\n if (this.drainTimer) { clearTimeout(this.drainTimer); this.drainTimer = undefined; this.drainScheduled = false; }\n while (this.pending.length > 0 || this.drainPromise) {\n if (this.pending.length > 0 && !this.drainPromise) this.startDrain();\n await this.drainPromise;\n }\n }\n\n async verify(): Promise<ChronicleVerifyResult> {\n await this.flush();\n const files = await collectPartitions(this.basePath);\n const checkpointResult = await readRetentionCheckpoint(this.basePath);\n if (checkpointResult.error) return { ok: false, entries: 0, brokenAt: 0, reason: checkpointResult.error };\n return verifyPartitionFiles(files, checkpointResult.checkpoint);\n }\n\n async purge(options: ChroniclePurgeOptions): Promise<ChroniclePurgeResult> {\n await this.flush();\n if (!Number.isFinite(options.retentionDays) || options.retentionDays <= 0) {\n throw new TypeError('Chronicle retentionDays must be a positive finite number');\n }\n await this.refreshStateFromDisk();\n const cutoff = Date.now() - options.retentionDays * 86400000;\n const activePath = path.resolve(this.path);\n const errors: ChroniclePurgeResult['errors'] = [];\n let dc = 0, db = 0, sc = 0;\n const suppliedFiles = options.files === undefined\n ? await collectJournalPartitions(this.basePath)\n : [...options.files];\n const eligible = new Set<string>();\n for (const suppliedPath of new Set(suppliedFiles)) {\n const file = path.resolve(suppliedPath);\n if (!isJournalPartition(file, path.dirname(this.basePath), this.basePath)) {\n errors.push({ file: suppliedPath, reason: 'not a Chronicle journal partition in this journal directory' });\n sc++;\n continue;\n }\n if (file === activePath) { sc++; continue; }\n let mtimeMs: number;\n try {\n const fileStat = await fs.lstat(file);\n if (!fileStat.isFile()) { sc++; continue; }\n mtimeMs = fileStat.mtimeMs;\n } catch (error) { if (isNotFound(error)) continue; errors.push({ file, reason: errorMessage(error) }); sc++; continue; }\n if (mtimeMs > cutoff) { sc++; continue; }\n eligible.add(file);\n }\n\n const candidates: string[] = [];\n const allPartitions = await collectJournalPartitions(this.basePath);\n for (const family of groupPartitionsByFamily(allPartitions).values()) {\n for (const file of family) {\n if (file === activePath || !eligible.has(file)) break;\n candidates.push(file);\n eligible.delete(file);\n }\n }\n sc += eligible.size;\n\n if (!options.dryRun) {\n for (const file of candidates) {\n try {\n const familyBase = partitionFamilyBase(file);\n let deletedBytes: number | undefined;\n await withFileLock(familyBase, async () => {\n const fileStat = await fs.lstat(file);\n if (!fileStat.isFile() || fileStat.mtimeMs > cutoff) return;\n const checkpointResult = await readRetentionCheckpoint(familyBase);\n if (checkpointResult.error) throw new Error(checkpointResult.error);\n const checkpoint = checkpointResult.checkpoint;\n const nextCheckpoint = await verifyRetainedPrefix(streamEntriesStrict(file), checkpoint);\n if (!nextCheckpoint) throw new Error('partition does not extend the trusted Chronicle chain');\n if (nextCheckpoint.sequence > (checkpoint?.sequence ?? 0)) {\n await writeRetentionCheckpoint(familyBase, nextCheckpoint);\n }\n deletedBytes = fileStat.size;\n await fs.unlink(file);\n });\n if (deletedBytes === undefined) { sc++; break; }\n db += deletedBytes;\n dc++;\n } catch (error) {\n errors.push({ file, reason: errorMessage(error) });\n sc++;\n // Candidates form an oldest-first prefix. Do not advance the\n // checkpoint beyond a partition that could not be removed: if its\n // checkpoint-covered bytes remain on disk, verify() must still be\n // able to anchor and validate them against that checkpoint.\n break;\n }\n }\n }\n return { deletedCount: dc, deletedBytes: db, skippedCount: sc, errors, ...(options.dryRun ? { candidates } : {}) };\n }\n\n private async maybeAutoPurge(): Promise<void> {\n if (this.retentionDays <= 0) return;\n const n = Date.now();\n if (n - this.lastAutoPurgeAt < this.autoPurgeIntervalMs) return;\n this.lastAutoPurgeAt = n;\n try { await this.purge({ retentionDays: this.retentionDays }); } catch { /* best-effort */ }\n }\n\n private scheduleDrain(): void {\n if (this.drainScheduled || this.drainPromise) return;\n this.drainScheduled = true;\n if (this.batchWindowMs === 0) {\n queueMicrotask(() => {\n this.drainScheduled = false;\n this.startDrain();\n });\n return;\n }\n this.drainTimer = setTimeout(() => { this.drainTimer = undefined; this.drainScheduled = false; this.startDrain(); }, this.batchWindowMs);\n }\n\n private startDrain(): void {\n if (this.drainPromise || this.pending.length === 0) return;\n const batch = this.pending.splice(0);\n const drain = this.persistBatch(batch);\n this.drainPromise = drain.finally(() => { this.drainPromise = undefined; if (this.pending.length > 0) this.scheduleDrain(); });\n }\n\n private async refreshStateFromDisk(): Promise<void> {\n const files = await collectPartitions(this.basePath);\n const latest = files[files.length - 1] ?? this.basePath;\n this.partitionIndex = partitionIndex(latest, this.basePath);\n const state = await readLastEntryState(latest);\n const entry = state.entry;\n // A non-empty active partition already carries the latest sequence and\n // hash-chain anchor. The retention checkpoint is only needed when no\n // retained event exists, so avoid opening (or probing for) the sidecar on\n // every normal append batch.\n const checkpointResult = entry ? {} : await readRetentionCheckpoint(this.basePath);\n if (checkpointResult.error) throw new Error(checkpointResult.error);\n const checkpoint = checkpointResult.checkpoint;\n this.lastSequence = entry?.sequence ?? checkpoint?.sequence ?? 0;\n this.lastHash = entry?.hash ?? checkpoint?.hash ?? GENESIS_HASH;\n this.partitionSizeBytes = state.size;\n this.partitionStartedAt = state.birthtimeMs ?? Date.now();\n this.stateInitialized = true;\n }\n\n private async canReuseDiskState(): Promise<boolean> {\n if (!this.stateInitialized) return false;\n const nextPartition = rotatedPath(this.basePath, this.partitionIndex + 1);\n const [currentStat, nextExists] = await Promise.all([\n fs.stat(this.path).catch((error: unknown) => {\n if (isNotFound(error)) return undefined;\n throw error;\n }),\n fs.access(nextPartition).then(\n () => true,\n (error: unknown) => {\n if (isNotFound(error)) return false;\n throw error;\n },\n ),\n ]);\n // Appends change the active partition size; rotations create the next\n // numbered partition. If neither happened since our last successful\n // batch, the cached sequence/hash anchor is still current and there is no\n // need to rescan the directory or read the JSONL tail again.\n return currentStat?.isFile() === true && currentStat.size === this.partitionSizeBytes && !nextExists;\n }\n\n private async checkRotation(): Promise<void> {\n if (this.partitionIndex === 0 && this.lastSequence === 0) return;\n if (Number.isFinite(this.rotationWindowMs) && Date.now() - this.partitionStartedAt >= this.rotationWindowMs) { this.rotate(); return; }\n if (Number.isFinite(this.maxPartitionSizeBytes) && this.partitionSizeBytes >= this.maxPartitionSizeBytes) this.rotate();\n }\n\n private rotate(): void { this.partitionIndex++; this.partitionStartedAt = Date.now(); this.partitionSizeBytes = 0; this.counters.partitionRolls++; }\n\n private async persistBatch(batch: typeof this.pending): Promise<void> {\n const started = performance.now();\n this.counters.batches++;\n this.counters.largestBatch = Math.max(this.counters.largestBatch, batch.length);\n try {\n let recorded: ChronicleEvent[] = [];\n await withFileLock(this.basePath, async () => {\n if (!(await this.canReuseDiskState())) await this.refreshStateFromDisk();\n await this.checkRotation();\n const cp = this.path;\n let prev: { sequence: number; hash: string } | undefined = this.lastSequence > 0 ? { sequence: this.lastSequence, hash: this.lastHash } : undefined;\n recorded = batch.map(({ input }) => {\n const instant = this.now().toISOString();\n const uh = { ...input, occurredAt: input.occurredAt ?? instant, monotonicNs: input.monotonicNs ?? this.monotonicNow().toString(), schemaVersion: CHRONICLE_SCHEMA_VERSION, eventId: this.idFactory(), observedAt: instant, persistedAt: instant, sequence: (prev?.sequence ?? 0) + 1, previousHash: prev?.hash ?? GENESIS_HASH };\n const event: ChronicleEvent = { ...uh, hash: hashValue(uh) };\n prev = event;\n return event;\n });\n const serialized = recorded.map((e) => JSON.stringify(e)).join('\\n') + '\\n';\n await fs.appendFile(cp, serialized, 'utf8');\n this.partitionSizeBytes += Buffer.byteLength(serialized);\n });\n const last = recorded[recorded.length - 1]!;\n this.lastSequence = last.sequence;\n this.lastHash = last.hash;\n batch.forEach((item, i) => { item.resolve(recorded[i]!); });\n this.counters.persistedEvents += batch.length;\n void this.maybeAutoPurge();\n } catch (error) {\n // appendFile can fail after a partial write. Force the next batch to\n // rebuild its chain anchor from disk instead of trusting local counters.\n this.stateInitialized = false;\n this.counters.failedEvents += batch.length;\n batch.forEach((item) => { item.reject(error); });\n } finally { this.lastBatchDurationMs = performance.now() - started; }\n }\n}\n\nfunction rotatedPath(basePath: string, index: number): string {\n const dir = path.dirname(basePath);\n const ext = path.extname(basePath);\n const base = path.basename(basePath, ext);\n return path.join(dir, `${base}.${String(index).padStart(5, '0')}${ext}`);\n}\n\n/**\n * Exported for the SQLite migration only (`legacy-journal-import.ts`).\n *\n * The importer has to walk partitions in exactly the order the writer produced\n * them and parse them with exactly the same strictness, so it reuses these\n * rather than growing a second implementation that could disagree about\n * rotation order or malformed lines. All three go away with the legacy reader\n * in phase 4 of `chronicle-sqlite-journal-v1`.\n */\nexport async function collectPartitions(basePath: string): Promise<string[]> {\n const dir = path.dirname(basePath);\n const ext = path.extname(basePath);\n const base = path.basename(basePath, ext);\n const pattern = new RegExp(`^${escapeRegex(base)}(?:\\\\.\\\\d{5})?${escapeRegex(ext)}$`);\n const result: string[] = [];\n try {\n const entries = await fs.readdir(dir, { withFileTypes: true });\n for (const entry of entries) if (entry.isFile() && pattern.test(entry.name)) result.push(path.join(dir, entry.name));\n } catch { /* ok */ }\n const baseFile = path.join(dir, base + ext);\n const rotated = result.filter((file) => file !== baseFile).sort((left, right) => parseIndex(left, base, ext) - parseIndex(right, base, ext));\n return [baseFile, ...rotated];\n}\n\nasync function collectJournalPartitions(basePath: string): Promise<string[]> {\n const directory = path.dirname(basePath);\n const result: string[] = [];\n try {\n const entries = await fs.readdir(directory, { withFileTypes: true });\n for (const entry of entries) {\n const file = path.join(directory, entry.name);\n if (entry.isFile() && isJournalPartition(file, directory, basePath)) result.push(file);\n }\n } catch { /* ok */ }\n return result.sort(comparePartitionPaths);\n}\n\nfunction isJournalPartition(filePath: string, directory: string, basePath?: string): boolean {\n if (path.dirname(path.resolve(filePath)) !== path.resolve(directory)) return false;\n const fileName = path.basename(filePath);\n if (!basePath) return false;\n const baseName = path.basename(basePath);\n const dailyFamily = /^\\d{4}-\\d{2}-\\d{2}\\.events(?:\\.\\d{5})?\\.jsonl$/;\n if (/^\\d{4}-\\d{2}-\\d{2}\\.events\\.jsonl$/.test(baseName)) return dailyFamily.test(fileName);\n return partitionFamilyBase(path.resolve(filePath)) === partitionFamilyBase(path.resolve(basePath));\n}\n\nfunction groupPartitionsByFamily(files: string[]): Map<string, string[]> {\n const groups = new Map<string, string[]>();\n for (const file of files) {\n const family = partitionFamilyBase(file);\n const group = groups.get(family) ?? [];\n group.push(file);\n groups.set(family, group);\n }\n return groups;\n}\n\nfunction partitionFamilyBase(filePath: string): string {\n return filePath.replace(/\\.\\d{5}(?=\\.jsonl$)/, '');\n}\n\nfunction retentionCheckpointPath(basePath: string): string {\n return `${partitionFamilyBase(basePath)}.retention.json`;\n}\n\nasync function verifyRetainedPrefix(\n entries: AsyncIterable<ChronicleEvent>,\n checkpoint: ChronicleRetentionCheckpoint | undefined,\n): Promise<ChronicleRetentionCheckpoint | undefined> {\n let sequence = checkpoint?.sequence ?? 0;\n let hash = checkpoint?.hash ?? GENESIS_HASH;\n let advanced = false;\n let sawEntry = false;\n for await (const entry of entries) {\n sawEntry = true;\n if (entry.sequence <= sequence) continue;\n if (entry.sequence !== sequence + 1 || entry.previousHash !== hash) return undefined;\n const { hash: recordedHash, ...content } = entry;\n if (hashValue(content) !== recordedHash) return undefined;\n sequence = entry.sequence;\n hash = recordedHash;\n advanced = true;\n }\n if (!sawEntry) return undefined;\n if (!advanced) return checkpoint;\n return { version: RETENTION_CHECKPOINT_VERSION, sequence, hash };\n}\n\nasync function verifyPartitionFiles(\n files: string[],\n checkpoint: ChronicleRetentionCheckpoint | undefined,\n): Promise<ChronicleVerifyResult> {\n const checkpointSequence = checkpoint?.sequence ?? 0;\n let previousHash = checkpoint?.hash ?? GENESIS_HASH;\n let entries = 0;\n let lastSequence = checkpointSequence;\n let coveredPrevious: ChronicleEvent | undefined;\n for (const file of files) {\n try {\n for await (const entry of streamEntriesStrict(file)) {\n const { hash: recordedHash, ...content } = entry;\n if (entry.sequence <= checkpointSequence) {\n // A checkpoint can be durably renamed just before its source\n // partition fails to unlink. Such retained bytes are still evidence:\n // validate them rather than treating every covered sequence as absent.\n if (hashValue(content) !== recordedHash) return { ok: false, entries, brokenAt: entries, reason: 'entry hash mismatch' };\n if (coveredPrevious && entry.sequence !== coveredPrevious.sequence + 1) {\n return { ok: false, entries, brokenAt: entries, reason: `sequence ${entry.sequence} is not ${coveredPrevious.sequence + 1}` };\n }\n if (coveredPrevious && entry.previousHash !== coveredPrevious.hash) {\n return { ok: false, entries, brokenAt: entries, reason: 'previous hash mismatch' };\n }\n if (entry.sequence === checkpointSequence && recordedHash !== checkpoint?.hash) {\n return { ok: false, entries, brokenAt: entries, reason: 'retention checkpoint hash mismatch' };\n }\n coveredPrevious = entry;\n continue;\n }\n const index = entries++;\n if (entry.sequence !== lastSequence + 1) return { ok: false, entries, brokenAt: index, reason: `sequence ${entry.sequence} is not ${lastSequence + 1}` };\n if (entry.previousHash !== previousHash) return { ok: false, entries, brokenAt: index, reason: 'previous hash mismatch' };\n if (hashValue(content) !== recordedHash) return { ok: false, entries, brokenAt: index, reason: 'entry hash mismatch' };\n previousHash = recordedHash;\n lastSequence = entry.sequence;\n }\n } catch (error) { return { ok: false, entries, brokenAt: entries, reason: errorMessage(error) }; }\n }\n if (\n coveredPrevious &&\n (coveredPrevious.sequence !== checkpointSequence || coveredPrevious.hash !== checkpoint?.hash)\n ) {\n return { ok: false, entries, brokenAt: entries, reason: 'retention checkpoint hash mismatch' };\n }\n return { ok: true, entries, lastSequence, lastHash: previousHash };\n}\n\nexport async function readRetentionCheckpoint(basePath: string): Promise<{\n checkpoint?: ChronicleRetentionCheckpoint | undefined;\n error?: string | undefined;\n}> {\n const checkpointPath = retentionCheckpointPath(basePath);\n let raw: string;\n try { raw = await fs.readFile(checkpointPath, 'utf8'); } catch (error) {\n return isNotFound(error) ? {} : { error: `cannot read retention checkpoint: ${errorMessage(error)}` };\n }\n try {\n const parsed = JSON.parse(raw) as Partial<ChronicleRetentionCheckpoint>;\n if (parsed.version !== RETENTION_CHECKPOINT_VERSION || !Number.isSafeInteger(parsed.sequence) || (parsed.sequence ?? -1) < 0 || !isHash(parsed.hash)) {\n return { error: 'invalid Chronicle retention checkpoint' };\n }\n return { checkpoint: parsed as ChronicleRetentionCheckpoint };\n } catch { return { error: 'invalid Chronicle retention checkpoint JSON' }; }\n}\n\nasync function writeRetentionCheckpoint(basePath: string, checkpoint: ChronicleRetentionCheckpoint): Promise<void> {\n await atomicWrite(retentionCheckpointPath(basePath), `${JSON.stringify(checkpoint)}\\n`, { mode: 0o600 });\n}\n\nfunction isHash(value: unknown): value is string {\n return typeof value === 'string' && /^[a-f0-9]{64}$/.test(value);\n}\n\nfunction parseIndex(filePath: string, base: string, ext: string): number {\n const suffix = path.basename(filePath).slice(base.length + 1, -ext.length);\n return suffix ? parseInt(suffix, 10) : 0;\n}\n\nfunction partitionIndex(filePath: string, basePath: string): number {\n const ext = path.extname(basePath);\n return parseIndex(filePath, path.basename(basePath, ext), ext);\n}\n\nfunction escapeRegex(text: string): string { return text.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\$&'); }\n\nasync function readLastEntryState(filePath: string): Promise<{\n entry?: ChronicleEvent | undefined;\n size: number;\n birthtimeMs?: number | undefined;\n}> {\n let handle: fs.FileHandle;\n try { handle = await fs.open(filePath, 'r'); } catch (error) { if (isNotFound(error)) return { size: 0 }; throw error; }\n try {\n const stat = await handle.stat();\n const size = stat.size;\n let position = size, suffix = '';\n while (position > 0) {\n const length = Math.min(65536, position);\n position -= length;\n const buf = Buffer.allocUnsafe(length);\n await handle.read(buf, 0, length, position);\n suffix = buf.toString('utf8') + suffix;\n const lines = suffix.split('\\n');\n const start = position === 0 ? 0 : 1;\n for (let i = lines.length - 1; i >= start; i--) {\n const trimmed = lines[i]!.trim();\n if (!trimmed) continue;\n try { return { entry: JSON.parse(trimmed) as ChronicleEvent, size, birthtimeMs: stat.birthtimeMs }; } catch { /* scan earlier */ }\n }\n suffix = lines[0] ?? '';\n }\n return { size, birthtimeMs: stat.birthtimeMs };\n } finally { await handle.close(); }\n}\n\n/** Stream entries line by line. Reading a whole partition into one string\n * breaks past V8's max string length (~512MB) \u2014 purge and verify must work\n * on partitions of any size, so only individual lines are materialized. */\nexport async function* streamEntriesStrict(filePath: string): AsyncGenerator<ChronicleEvent> {\n let lineNumber = 0;\n try {\n const input = createReadStream(filePath, { encoding: 'utf8', highWaterMark: 256 * 1024 });\n const lines = createInterface({ input, crlfDelay: Infinity });\n for await (const line of lines) {\n lineNumber++;\n const trimmed = line.trim();\n if (!trimmed) continue;\n let entry: ChronicleEvent;\n try { entry = JSON.parse(trimmed) as ChronicleEvent; } catch { throw new Error(`invalid JSON at line ${lineNumber} in ${path.basename(filePath)}`); }\n yield entry;\n }\n } catch (error) {\n if (isNotFound(error)) return;\n throw error;\n }\n}\n\nasync function readEntriesStrict(filePath: string): Promise<ChronicleEvent[]> {\n const entries: ChronicleEvent[] = [];\n for await (const entry of streamEntriesStrict(filePath)) entries.push(entry);\n return entries;\n}\n\nfunction isNotFound(error: unknown): boolean { return typeof error === 'object' && error !== null && 'code' in error && error.code === 'ENOENT'; }\nfunction errorMessage(error: unknown): string { return error instanceof Error ? error.message : String(error); }\n\nexport { GENESIS_HASH };\n", "import type { FileHandle } from 'node:fs/promises';\nimport {\n type AtomicWriteOptions,\n createPersistencePrimitives,\n type FileLockOptions,\n} from '@wrongstack/persistence';\nimport { FsError } from '../types/errors.js';\n\nexport type { AtomicWriteOptions, FileLockOptions } from '@wrongstack/persistence';\n\nconst primitives = createPersistencePrimitives({\n createLockTimeoutError: ({ targetPath, timeoutMs }) =>\n new FsError({\n message: `Timed out waiting for file lock: ${targetPath}`,\n code: 'FS_ATOMIC_WRITE_FAILED',\n path: targetPath,\n context: { timeoutMs },\n }),\n});\n\nexport const atomicWrite: (\n targetPath: string,\n content: string | Uint8Array,\n opts?: AtomicWriteOptions,\n) => Promise<void> = primitives.atomicWrite;\n/**\n * Atomic replace that streams its new contents instead of taking them as one\n * buffer. Use when the replacement is large enough that materializing it would\n * itself be the memory problem (log rotation, tail compaction).\n */\nexport const atomicReplaceWithWriter: <T>(\n targetPath: string,\n write: (handle: FileHandle) => Promise<T>,\n opts?: AtomicWriteOptions,\n) => Promise<T> = primitives.atomicReplaceWithWriter;\nexport const ensureDir: (dir: string) => Promise<void> = primitives.ensureDir;\nexport const withFileLock: <T>(\n targetPath: string,\n fn: () => Promise<T>,\n opts?: FileLockOptions,\n) => Promise<T> = primitives.withFileLock;\n", "import { toErrorMessage } from '../utils/error.js';\n\n/**\n * WrongStack error hierarchy.\n *\n * Every error thrown by the framework is a `WrongStackError` with a\n * machine-readable `code`, a `subsystem` tag, and a `severity` level.\n * This lets consumers (CLI, TUI, plugins, tests) branch on structured\n * data instead of parsing error messages.\n */\n\n// \u2500\u2500 Error codes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n/**\n * Machine-readable error codes as frozen constants.\n *\n * Use `ERROR_CODES.X` instead of raw string literals for:\n * - IDE autocomplete and compile-time validation\n * - Safe refactoring (rename updates all usages)\n * - Plugin extensibility (extend the object to add custom codes)\n *\n * The `ErrorCode` type is derived from this object, so adding a new\n * code here automatically updates the type without extra changes.\n */\nexport const ERROR_CODES = {\n // Provider\n PROVIDER_RATE_LIMITED: 'PROVIDER_RATE_LIMITED',\n PROVIDER_AUTH_FAILED: 'PROVIDER_AUTH_FAILED',\n PROVIDER_OVERLOADED: 'PROVIDER_OVERLOADED',\n PROVIDER_INVALID_REQUEST: 'PROVIDER_INVALID_REQUEST',\n PROVIDER_SERVER_ERROR: 'PROVIDER_SERVER_ERROR',\n PROVIDER_NETWORK_ERROR: 'PROVIDER_NETWORK_ERROR',\n PROVIDER_CONTEXT_OVERFLOW: 'PROVIDER_CONTEXT_OVERFLOW',\n // Tool\n TOOL_NOT_FOUND: 'TOOL_NOT_FOUND',\n TOOL_PERMISSION_DENIED: 'TOOL_PERMISSION_DENIED',\n TOOL_EXECUTION_FAILED: 'TOOL_EXECUTION_FAILED',\n TOOL_TIMEOUT: 'TOOL_TIMEOUT',\n TOOL_INPUT_INVALID: 'TOOL_INPUT_INVALID',\n // Config\n CONFIG_INVALID: 'CONFIG_INVALID',\n CONFIG_NOT_FOUND: 'CONFIG_NOT_FOUND',\n CONFIG_PARSE_FAILED: 'CONFIG_PARSE_FAILED',\n CONFIG_MIGRATION_NEEDED: 'CONFIG_MIGRATION_NEEDED',\n // Plugin\n PLUGIN_LOAD_FAILED: 'PLUGIN_LOAD_FAILED',\n PLUGIN_API_MISMATCH: 'PLUGIN_API_MISMATCH',\n PLUGIN_MISSING_DEPENDENCY: 'PLUGIN_MISSING_DEPENDENCY',\n // Agent\n AGENT_ITERATION_LIMIT: 'AGENT_ITERATION_LIMIT',\n AGENT_CONTEXT_OVERFLOW: 'AGENT_CONTEXT_OVERFLOW',\n AGENT_ABORTED: 'AGENT_ABORTED',\n AGENT_RUN_FAILED: 'AGENT_RUN_FAILED',\n // Session\n SESSION_NOT_FOUND: 'SESSION_NOT_FOUND',\n SESSION_CORRUPTED: 'SESSION_CORRUPTED',\n SESSION_WRITE_FAILED: 'SESSION_WRITE_FAILED',\n // Container / Registry\n CONTAINER_TOKEN_ALREADY_BOUND: 'CONTAINER_TOKEN_ALREADY_BOUND',\n CONTAINER_TOKEN_NOT_BOUND: 'CONTAINER_TOKEN_NOT_BOUND',\n CONTAINER_CIRCULAR_DEPENDENCY: 'CONTAINER_CIRCULAR_DEPENDENCY',\n REGISTRY_DUPLICATE: 'REGISTRY_DUPLICATE',\n REGISTRY_NOT_FOUND: 'REGISTRY_NOT_FOUND',\n REGISTRY_INVALID: 'REGISTRY_INVALID',\n // File system\n FS_READ_FAILED: 'FS_READ_FAILED',\n FS_WRITE_FAILED: 'FS_WRITE_FAILED',\n FS_MKDIR_FAILED: 'FS_MKDIR_FAILED',\n FS_DELETE_FAILED: 'FS_DELETE_FAILED',\n FS_ATOMIC_WRITE_FAILED: 'FS_ATOMIC_WRITE_FAILED',\n // SDD (Spec-Driven Development)\n SDD_VALIDATION_FAILED: 'SDD_VALIDATION_FAILED',\n SDD_PARSE_FAILED: 'SDD_PARSE_FAILED',\n SDD_INVALID_STATE: 'SDD_INVALID_STATE',\n SDD_NOT_READY: 'SDD_NOT_READY',\n // General\n VALIDATION_ERROR: 'VALIDATION_ERROR',\n PARSE_FAILED: 'PARSE_FAILED',\n UNKNOWN: 'UNKNOWN',\n} as const;\n\n/**\n * Union type derived from `ERROR_CODES`. Using `typeof ERROR_CODES[keyof typeof ERROR_CODES]`\n * instead of a string literal union means TypeScript auto-updates the type whenever\n * a new code is added to `ERROR_CODES` \u2014 no need to keep two lists in sync.\n */\nexport type ErrorCode = (typeof ERROR_CODES)[keyof typeof ERROR_CODES];\n\nexport type ErrorSubsystem =\n | 'provider'\n | 'tool'\n | 'config'\n | 'plugin'\n | 'agent'\n | 'session'\n | 'sdd'\n | 'container'\n | 'fs'\n | 'general';\nexport type ErrorSeverity = 'fatal' | 'error' | 'warning';\n\n// \u2500\u2500 Base error class \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport class WrongStackError extends Error {\n readonly code: ErrorCode;\n readonly subsystem: ErrorSubsystem;\n readonly severity: ErrorSeverity;\n readonly recoverable: boolean;\n readonly context?: Record<string, unknown> | undefined;\n\n constructor(opts: {\n message: string;\n code: ErrorCode;\n subsystem: ErrorSubsystem;\n severity?: ErrorSeverity | undefined;\n recoverable?: boolean | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super(opts.message, { cause: opts.cause });\n this.name = 'WrongStackError';\n this.code = opts.code;\n this.subsystem = opts.subsystem;\n this.severity = opts.severity ?? 'error';\n this.recoverable = opts.recoverable ?? false;\n this.context = opts.context;\n }\n\n /**\n * Render a one-line user-facing description.\n * Subclasses should override for domain-specific formatting.\n */\n describe(): string {\n const ctx = this.context ? ` ${formatContext(this.context)}` : '';\n return `${this.code}: ${this.message}${ctx}`;\n }\n}\n\nfunction formatContext(ctx: Record<string, unknown>): string {\n const parts = Object.entries(ctx)\n .filter(([, v]) => v !== undefined)\n .slice(0, 3)\n .map(([k, v]) => `${k}=${String(v)}`);\n return parts.length > 0 ? `[${parts.join(' ')}]` : '';\n}\n\n// \u2500\u2500 Specific error classes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n/**\n * Tool execution errors \u2014 thrown by ToolExecutor and individual tools.\n */\nexport class ToolError extends WrongStackError {\n readonly toolName: string;\n\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n | 'TOOL_NOT_FOUND'\n | 'TOOL_PERMISSION_DENIED'\n | 'TOOL_EXECUTION_FAILED'\n | 'TOOL_TIMEOUT'\n | 'TOOL_INPUT_INVALID'\n >;\n toolName: string;\n recoverable?: boolean | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'tool',\n recoverable: opts.recoverable,\n context: { tool: opts.toolName, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'ToolError';\n this.toolName = opts.toolName;\n }\n}\n\n/**\n * Config loading / validation errors.\n */\nexport class ConfigError extends WrongStackError {\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n 'CONFIG_INVALID' | 'CONFIG_NOT_FOUND' | 'CONFIG_PARSE_FAILED' | 'CONFIG_MIGRATION_NEEDED'\n >;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'config',\n severity: 'fatal',\n recoverable: false,\n context: opts.context,\n cause: opts.cause,\n });\n this.name = 'ConfigError';\n }\n}\n\n/**\n * Plugin loading / lifecycle errors.\n */\nexport class PluginError extends WrongStackError {\n readonly pluginName: string;\n\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n 'PLUGIN_LOAD_FAILED' | 'PLUGIN_API_MISMATCH' | 'PLUGIN_MISSING_DEPENDENCY'\n >;\n pluginName: string;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'plugin',\n severity: 'error',\n recoverable: opts.code === ERROR_CODES.PLUGIN_MISSING_DEPENDENCY,\n context: { plugin: opts.pluginName, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'PluginError';\n this.pluginName = opts.pluginName;\n }\n}\n\n/**\n * Agent runtime errors \u2014 thrown by Agent.run when a non-WrongStackError\n * escapes the inner loop, so callers always see a structured error.\n */\nexport class AgentError extends WrongStackError {\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n 'AGENT_ITERATION_LIMIT' | 'AGENT_CONTEXT_OVERFLOW' | 'AGENT_ABORTED' | 'AGENT_RUN_FAILED'\n >;\n recoverable?: boolean | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'agent',\n severity: opts.code === ERROR_CODES.AGENT_ABORTED ? 'warning' : 'error',\n recoverable: opts.recoverable ?? opts.code === ERROR_CODES.AGENT_ITERATION_LIMIT,\n context: opts.context,\n cause: opts.cause,\n });\n this.name = 'AgentError';\n }\n}\n\n/**\n * Wrap an arbitrary thrown value into a `WrongStackError` so the caller\n * always gets a structured error. Pass-throughs WrongStackError instances\n * unchanged; raw `Error`s and primitives get an `AGENT_RUN_FAILED` wrapper\n * with the original preserved as `cause`.\n */\nexport function toWrongStackError(\n err: unknown,\n code: Extract<ErrorCode, 'AGENT_RUN_FAILED' | 'AGENT_ABORTED' | 'UNKNOWN'> = ERROR_CODES.AGENT_RUN_FAILED,\n): WrongStackError {\n if (err instanceof WrongStackError) return err;\n const message = toErrorMessage(err);\n return new AgentError({\n message,\n code: code === 'UNKNOWN' ? ERROR_CODES.AGENT_RUN_FAILED : code,\n cause: err,\n });\n}\n\n/**\n * Session storage errors.\n */\nexport class SessionError extends WrongStackError {\n readonly sessionId?: string | undefined;\n\n constructor(opts: {\n message: string;\n code: Extract<ErrorCode, 'SESSION_NOT_FOUND' | 'SESSION_CORRUPTED' | 'SESSION_WRITE_FAILED'>;\n sessionId?: string | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'session',\n severity: opts.code === ERROR_CODES.SESSION_WRITE_FAILED ? 'error' : 'warning',\n recoverable: opts.code !== ERROR_CODES.SESSION_CORRUPTED,\n context: { sessionId: opts.sessionId, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'SessionError';\n this.sessionId = opts.sessionId;\n }\n}\n\n/**\n * SDD (Spec-Driven Development) errors \u2014 spec validation, parsing, and\n * state machine violations in the AISpecBuilder, TaskFlow, and TaskTracker.\n */\nexport class SddError extends WrongStackError {\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n 'SDD_VALIDATION_FAILED' | 'SDD_PARSE_FAILED' | 'SDD_INVALID_STATE' | 'SDD_NOT_READY'\n >;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'sdd',\n severity: opts.code === ERROR_CODES.SDD_PARSE_FAILED ? 'warning' : 'error',\n recoverable: opts.code === ERROR_CODES.SDD_NOT_READY,\n context: opts.context,\n cause: opts.cause,\n });\n this.name = 'SddError';\n }\n}\n\n/**\n * File system operation errors.\n */\nexport class FsError extends WrongStackError {\n readonly path?: string | undefined;\n\n constructor(opts: {\n message: string;\n code: Extract<\n ErrorCode,\n 'FS_READ_FAILED' | 'FS_WRITE_FAILED' | 'FS_MKDIR_FAILED' | 'FS_DELETE_FAILED' | 'FS_ATOMIC_WRITE_FAILED'\n >;\n path?: string | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: opts.code,\n subsystem: 'fs',\n severity: 'error',\n recoverable: opts.code !== ERROR_CODES.FS_READ_FAILED,\n context: { path: opts.path, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'FsError';\n this.path = opts.path;\n }\n}\n\n/**\n * HTTP fetch error \u2014 thrown when a network request returns a non-OK status.\n * Carries the response status so {@link classifyToolError} can branch on it\n * (429 \u2192 transient, 404 \u2192 not_found, 401 \u2192 permission) without duck-typing\n * the error via `'response' in err`.\n *\n * P3 #18 (before-release.md): the previous `'response' in err` check caught\n * any Error with a `response` property, including custom errors, proxy\n * objects, or mocked errors in tests. `instanceof FetchError` is reliable.\n *\n * Tools and providers that make HTTP requests and need the executor to\n * classify their failures should throw `new FetchError({ status, message })`\n * instead of a bare `Error` with an ad-hoc `response` field.\n */\nexport class FetchError extends WrongStackError {\n readonly status: number;\n\n constructor(opts: {\n message: string;\n status: number;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: ERROR_CODES.VALIDATION_ERROR,\n subsystem: 'general',\n severity: 'error',\n recoverable: opts.status === 429 || opts.status >= 500,\n context: { status: opts.status, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'FetchError';\n this.status = opts.status;\n }\n}\n\n/**\n * Tool input validation error \u2014 thrown when a tool's input fails a validation\n * check that the JSON Schema cannot express (e.g. `old_string === new_string`\n * in edit, or a cross-field invariant). Use this instead of a bare\n * `throw new Error('...validation...')` so {@link classifyToolError} can\n * match on `instanceof` rather than a locale-dependent message substring.\n *\n * P2 #6 (before-release.md): the previous `err.message.includes('validation')`\n * check misclassified any error whose message happened to contain \"validation\"\n * (e.g. a third-party \"input validation timeout\") as a VALIDATION error.\n *\n * Named `ToolValidationError` (not `ValidationError`) to avoid colliding with\n * the existing `ValidationError` interface exported by json-schema-validate.ts\n * (a validation-result shape, not an Error subclass).\n */\nexport class ToolValidationError extends WrongStackError {\n constructor(opts: {\n message: string;\n /** Field path or tool name that failed validation, for diagnostics. */\n field?: string | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: ERROR_CODES.VALIDATION_ERROR,\n subsystem: 'general',\n severity: 'error',\n recoverable: false,\n context: { field: opts.field, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'ToolValidationError';\n }\n}\n\n/**\n * Response / payload parse error \u2014 thrown when an upstream HTTP response,\n * file, or data structure is well-formed at the transport layer (HTTP 200,\n * valid JSON) but is missing required fields or has an unexpected shape.\n *\n * Distinct from `ConfigError(CONFIG_PARSE_FAILED)` (which is specifically\n * for config-file parsing) and `FetchError` (which covers HTTP non-OK\n * responses). `ParseError` fills the gap: the request succeeded but the\n * response body couldn't be interpreted.\n *\n * Common sites: OAuth token responses missing `access_token`, device-code\n * responses missing `device_code`, registry responses with unexpected\n * schemas.\n */\nexport class ParseError extends WrongStackError {\n readonly source?: string | undefined;\n\n constructor(opts: {\n message: string;\n /**\n * What was being parsed \u2014 e.g. `'oauth-token-response'`,\n * `'device-code-response'`. Lets consumers distinguish parse failures\n * from different upstream APIs without parsing the message.\n */\n source?: string | undefined;\n context?: Record<string, unknown> | undefined;\n cause?: unknown | undefined;\n }) {\n super({\n message: opts.message,\n code: ERROR_CODES.PARSE_FAILED,\n subsystem: 'general',\n severity: 'error',\n recoverable: false,\n context: { source: opts.source, ...opts.context },\n cause: opts.cause,\n });\n this.name = 'ParseError';\n this.source = opts.source;\n }\n}\n\n// \u2500\u2500 Type guards \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport function isWrongStackError(err: unknown): err is WrongStackError {\n return err instanceof WrongStackError;\n}\n\nexport function isToolError(err: unknown): err is ToolError {\n return err instanceof ToolError;\n}\n\nexport function isConfigError(err: unknown): err is ConfigError {\n return err instanceof ConfigError;\n}\n\nexport function isPluginError(err: unknown): err is PluginError {\n return err instanceof PluginError;\n}\n\nexport function isSessionError(err: unknown): err is SessionError {\n return err instanceof SessionError;\n}\n\nexport function isAgentError(err: unknown): err is AgentError {\n return err instanceof AgentError;\n}\n\nexport function isFsError(err: unknown): err is FsError {\n return err instanceof FsError;\n}\n\nexport function isToolValidationError(err: unknown): err is ToolValidationError {\n return err instanceof ToolValidationError;\n}\n\nexport function isFetchError(err: unknown): err is FetchError {\n return err instanceof FetchError;\n}\n\nexport function isParseError(err: unknown): err is ParseError {\n return err instanceof ParseError;\n}\n\nexport function isSddError(err: unknown): err is SddError {\n return err instanceof SddError;\n}\n", "/**\n * The one implementation of Chronicle's tamper-evident hash.\n *\n * Chronicle events form a chain: each carries the `hash` of its predecessor in\n * `previousHash`, anchored at {@link GENESIS_HASH}. Verification recomputes\n * every `hash` from the stored event, so the canonicalization below is part of\n * the durable format \u2014 two subtly different implementations would produce two\n * incompatible chains, and the divergence would only surface later as a\n * \"corrupt journal\" report on data that was never actually tampered with.\n *\n * It therefore lives here rather than beside any one store, and both the JSONL\n * journal and the SQLite journal import it.\n */\nimport { createHash } from 'node:crypto';\nimport type { ChronicleEvent } from './types.js';\n\n/** `previousHash` of the first event in a chain. */\nexport const GENESIS_HASH = '0'.repeat(64);\n\n/**\n * Deterministic JSON encoding: object keys sorted, `undefined` members dropped,\n * `undefined` array elements encoded as `null`.\n *\n * Note this is NOT what gets written to disk \u2014 the JSONL journal stores\n * `JSON.stringify(event)` in V8 property order. The stored bytes are a record;\n * the preimage is always re-derived from the parsed event.\n */\nexport function stableStringify(value: unknown): string {\n if (value === null || typeof value !== 'object') return JSON.stringify(value);\n if (Array.isArray(value)) {\n return `[${value.map((item) => (item === undefined ? 'null' : stableStringify(item))).join(',')}]`;\n }\n const obj = value as Record<string, unknown>;\n return `{${Object.keys(obj)\n .sort()\n .filter((key) => obj[key] !== undefined)\n .map((key) => `${JSON.stringify(key)}:${stableStringify(obj[key])}`)\n .join(',')}}`;\n}\n\nexport function hashValue(value: unknown): string {\n return createHash('sha256').update(stableStringify(value), 'utf8').digest('hex');\n}\n\n/**\n * Recompute the hash a stored event should carry.\n *\n * The `hash` field is excluded from its own preimage, so verification of an\n * event read back from any store is `chronicleEventHash(event) === event.hash`.\n */\nexport function chronicleEventHash(event: ChronicleEvent): string {\n const { hash: _hash, ...unhashed } = event;\n return hashValue(unhashed);\n}\n", "import * as path from 'node:path';\n\n/** Matches both rotated (`*.events.NNNNN.jsonl`) and unrotated (`*.events.jsonl`) partition files. */\nexport const PARTITION_FILE_PATTERN = /^(.*\\.events)(?:\\.(\\d{5}))?\\.jsonl$/;\n\nfunction partitionFamily(filePath: string): string {\n const match = PARTITION_FILE_PATTERN.exec(path.basename(filePath));\n return path.join(path.dirname(filePath), match?.[1] ?? path.basename(filePath));\n}\n\nfunction partitionSequence(filePath: string): number {\n const match = PARTITION_FILE_PATTERN.exec(path.basename(filePath));\n return Number(match?.[2] ?? 0);\n}\n\n/** Orders partitions by family, then by rotation sequence \u2014 the unrotated file (no sequence) sorts first. */\nexport function comparePartitionPaths(left: string, right: string): number {\n const familyOrder = partitionFamily(left).localeCompare(partitionFamily(right));\n return familyOrder || partitionSequence(left) - partitionSequence(right);\n}\n", "/** Schema version for the first durable WrongStack Chronicle event envelope. */\nexport const CHRONICLE_SCHEMA_VERSION = 1 as const;\n\nexport type ChronicleOutcome =\n | 'started'\n | 'success'\n | 'failure'\n | 'cancelled'\n | 'denied'\n | 'abandoned'\n | 'unknown';\n\n/** Stable identities used to project one event into global and project views. */\nexport interface ChronicleScope {\n installationId: string;\n machineId: string;\n projectId?: string | undefined;\n repositoryId?: string | undefined;\n workspaceId?: string | undefined;\n worktreeId?: string | undefined;\n sessionId?: string | undefined;\n turnId?: string | undefined;\n iterationId?: string | undefined;\n agentId?: string | undefined;\n goalId?: string | undefined;\n planId?: string | undefined;\n taskId?: string | undefined;\n kanbanBoardId?: string | undefined;\n}\n\nexport interface ChronicleCorrelation {\n traceId: string;\n spanId: string;\n parentSpanId?: string | undefined;\n logicalRequestId?: string | undefined;\n attemptId?: string | undefined;\n toolCallId?: string | undefined;\n}\n\nexport interface ChronicleRuntimeIdentity {\n providerId?: string | undefined;\n modelId?: string | undefined;\n modelRevision?: string | undefined;\n processId?: number | undefined;\n parentProcessId?: number | undefined;\n}\n\nexport interface ChronicleResourceRef {\n kind: 'file' | 'symbol' | 'memory' | 'task' | 'kanban' | 'process' | 'network' | 'artifact' | 'other';\n id: string;\n path?: string | undefined;\n lineStart?: number | undefined;\n lineEnd?: number | undefined;\n contentHashBefore?: string | undefined;\n contentHashAfter?: string | undefined;\n}\n\nexport interface ChronicleEventInput {\n eventType: string;\n scope: ChronicleScope;\n correlation: ChronicleCorrelation;\n runtime?: ChronicleRuntimeIdentity | undefined;\n resource?: ChronicleResourceRef | undefined;\n outcome?: ChronicleOutcome | undefined;\n durationNs?: string | undefined;\n occurredAt?: string | undefined;\n monotonicNs?: string | undefined;\n attributes?: Record<string, unknown> | undefined;\n tags?: Record<string, string> | undefined;\n}\n\n/**\n * Lossless durable envelope. All wall-clock timestamps are UTC ISO-8601;\n * monotonicNs is used for elapsed-time ordering inside one process.\n */\nexport interface ChronicleEvent extends ChronicleEventInput {\n schemaVersion: typeof CHRONICLE_SCHEMA_VERSION;\n eventId: string;\n observedAt: string;\n persistedAt: string;\n sequence: number;\n previousHash: string;\n hash: string;\n}\n\nexport type ChronicleVerifyResult =\n | { ok: true; entries: number; lastSequence: number; lastHash: string }\n | { ok: false; entries: number; brokenAt: number; reason: string };\n", "/**\n * ChronicleMetricsStore \u2014 derived, queryable aggregates over the raw\n * Chronicle journal (\"process, don't hoard\").\n *\n * The journal is the durable evidence log; this store is a disposable\n * projection kept in `<chronicleDir>/metrics.db` (node:sqlite, WAL). Each\n * `refresh()` incrementally consumes only the journal bytes appended since\n * the previous run (per-partition byte offsets in `ingest_state`), so the\n * raw JSONL partitions can be purged by retention without losing metrics:\n *\n * - `provider_daily` \u2014 provider\u00D7model\u00D7day attempt/success/failure/retry/\n * fallback counts, token totals, duration stats.\n * - `task_outcomes` \u2014 one row per task (kanban/SDD/subagent) with status,\n * timing, retry counts, and board/run/session lineage.\n * - `file_lineage` \u2014 one row per observed file mutation with full\n * session/agent/task/board/tool/model attribution.\n * - `token_cost` \u2014 latest cumulative token.accounted cost snapshot per\n * scope (same latest-wins semantics as the query\n * engine's summary).\n * - `daily_counters`, `family_daily`, `agent_daily`, `logical_request_daily`,\n * `file_seen_daily` \u2014 per-day scalar counters and dedup sets backing\n * `defaultSummary()`, a `ChronicleSummary` for the common unfiltered/\n * time-bounded dashboard view. Any genuinely ad hoc filter (free text,\n * path, session, provider, model) falls back to the raw-scan summary in\n * query.ts \u2014 fixed-dimension aggregation fundamentally can't answer those.\n *\n * The schema is a cache: on version mismatch it is dropped and re-ingested\n * from whatever journal partitions still exist.\n */\n\nimport * as fs from 'node:fs/promises';\nimport { createRequire } from 'node:module';\nimport * as path from 'node:path';\nimport type { DatabaseSync } from 'node:sqlite';\nimport { withFileLock } from '../utils/atomic-write.js';\nimport { withSqliteExperimentalWarningSuppressed } from '../utils/sqlite-warning.js';\nimport { findChroniclePartitions, isTerminalFailure, signalFamily } from './query.js';\nimport type { ChronicleEvent } from './types.js';\nimport type { ChronicleSignalFamily, ChronicleSummary } from './query.js';\n\nconst SCHEMA_VERSION = 3;\nconst READ_CHUNK_BYTES = 1024 * 1024;\nconst EMPTY_FAMILIES: Record<ChronicleSignalFamily, number> = {\n llm: 0, agent: 0, tool: 0, file: 0, memory: 0, task: 0, decision: 0, runtime: 0, finding: 0,\n};\n\nexport interface ChronicleMetricsRefreshResult {\n ingestedEvents: number;\n ingestedBytes: number;\n sourceFiles: number;\n invalidLines: number;\n}\n\nexport interface ChronicleProviderDailyRow {\n day: string;\n providerId: string;\n modelId: string;\n attempts: number;\n completed: number;\n failed: number;\n retries: number;\n fallbacks: number;\n inputTokens: number;\n outputTokens: number;\n cacheReadTokens: number;\n cacheWriteTokens: number;\n avgDurationMs: number;\n maxDurationMs: number;\n}\n\nexport interface ChronicleTaskOutcomeRow {\n taskId: string;\n runId: string;\n boardId: string;\n sessionId: string;\n agentId: string;\n status: string;\n startedAt: string | null;\n endedAt: string | null;\n durationMs: number | null;\n retries: number;\n verificationFailures: number;\n filesTouched: number;\n}\n\nexport interface ChronicleFileLineageRow {\n path: string;\n operation: string;\n occurredAt: string;\n sessionId: string;\n agentId: string;\n taskId: string;\n boardId: string;\n runId: string;\n toolName: string;\n providerId: string;\n modelId: string;\n source: string;\n}\n\nexport interface ChronicleMetricsSummary {\n providers: { attempts: number; completed: number; failed: number; successRate: number };\n tasks: Record<string, number>;\n files: { mutations: number; uniquePaths: number };\n estimatedCostUsd: number;\n}\n\n// \u2500\u2500\u2500 node:sqlite lazy loader (mirrors SAGE's pattern, compacted) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nlet Ctor: typeof DatabaseSync | null | undefined;\n\nfunction loadDatabaseSync(): typeof DatabaseSync {\n if (Ctor) return Ctor;\n if (Ctor === null) throw new Error('node:sqlite is unavailable in this runtime');\n try {\n Ctor = withSqliteExperimentalWarningSuppressed(\n () => (createRequire(import.meta.url)('node:sqlite') as typeof import('node:sqlite')).DatabaseSync,\n );\n return Ctor;\n } catch (error) {\n Ctor = null;\n throw new Error(\n \"Chronicle metrics need Node's built-in SQLite (node:sqlite, Node >= 22.5): \" +\n (error instanceof Error ? error.message : String(error)),\n );\n }\n}\n\n/** Non-throwing availability probe for callers that degrade gracefully. */\nexport function isChronicleMetricsAvailable(): boolean {\n try {\n loadDatabaseSync();\n return true;\n } catch {\n return false;\n }\n}\n\n// \u2500\u2500\u2500 Store \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport class ChronicleMetricsStore {\n private readonly db: DatabaseSync;\n private readonly directory: string;\n private readonly dbPath: string;\n\n private constructor(directory: string) {\n this.directory = path.resolve(directory);\n this.dbPath = path.join(this.directory, 'metrics.db');\n const Database = loadDatabaseSync();\n this.db = new Database(this.dbPath);\n this.db.exec('PRAGMA journal_mode = WAL');\n this.ensureSchema();\n }\n\n static open(chronicleDirectory: string): ChronicleMetricsStore {\n return new ChronicleMetricsStore(chronicleDirectory);\n }\n\n close(): void {\n this.db.close();\n }\n\n /** Incrementally ingest journal bytes appended since the last refresh.\n * Safe across processes: guarded by a file lock on the database path. */\n async refresh(): Promise<ChronicleMetricsRefreshResult> {\n const result: ChronicleMetricsRefreshResult = {\n ingestedEvents: 0,\n ingestedBytes: 0,\n sourceFiles: 0,\n invalidLines: 0,\n };\n await withFileLock(this.dbPath, async () => {\n const files = await findChroniclePartitions(this.directory);\n const offsets = this.loadOffsets();\n for (const file of files) {\n const key = normalizeKey(path.relative(this.directory, file));\n const consumed = offsets.get(key) ?? 0;\n const ingested = await this.ingestFile(file, key, consumed, result);\n if (ingested) result.sourceFiles++;\n }\n this.pruneOffsets(files);\n });\n return result;\n }\n\n providerDaily(options: { from?: string; to?: string } = {}): ChronicleProviderDailyRow[] {\n const clauses: string[] = [];\n const params: string[] = [];\n if (options.from) {\n clauses.push('day >= ?');\n params.push(options.from.slice(0, 10));\n }\n if (options.to) {\n clauses.push('day <= ?');\n params.push(options.to.slice(0, 10));\n }\n const where = clauses.length > 0 ? ` WHERE ${clauses.join(' AND ')}` : '';\n const rows = this.db\n .prepare(\n `SELECT day, provider_id, model_id, attempts, completed, failed, retries, fallbacks,\n input_tokens, output_tokens, cache_read_tokens, cache_write_tokens,\n duration_ms_total, duration_ms_max, duration_count\n FROM provider_daily${where} ORDER BY day DESC, provider_id, model_id`,\n )\n .all(...params) as Array<Record<string, string | number>>;\n return rows.map((row) => ({\n day: String(row.day),\n providerId: String(row.provider_id),\n modelId: String(row.model_id),\n attempts: Number(row.attempts),\n completed: Number(row.completed),\n failed: Number(row.failed),\n retries: Number(row.retries),\n fallbacks: Number(row.fallbacks),\n inputTokens: Number(row.input_tokens),\n outputTokens: Number(row.output_tokens),\n cacheReadTokens: Number(row.cache_read_tokens),\n cacheWriteTokens: Number(row.cache_write_tokens),\n avgDurationMs:\n Number(row.duration_count) > 0\n ? Number(row.duration_ms_total) / Number(row.duration_count)\n : 0,\n maxDurationMs: Number(row.duration_ms_max),\n }));\n }\n\n taskOutcomes(\n options: {\n runId?: string;\n boardId?: string;\n sessionId?: string;\n status?: string;\n limit?: number;\n } = {},\n ): ChronicleTaskOutcomeRow[] {\n const clauses: string[] = [];\n const params: Array<string | number> = [];\n if (options.runId) {\n clauses.push('t.run_id = ?');\n params.push(options.runId);\n }\n if (options.boardId) {\n clauses.push('t.board_id = ?');\n params.push(options.boardId);\n }\n if (options.sessionId) {\n clauses.push('t.session_id = ?');\n params.push(options.sessionId);\n }\n if (options.status) {\n clauses.push('t.status = ?');\n params.push(options.status);\n }\n const where = clauses.length > 0 ? ` WHERE ${clauses.join(' AND ')}` : '';\n params.push(clampLimit(options.limit, 100));\n const rows = this.db\n .prepare(\n `SELECT t.*, (SELECT COUNT(*) FROM file_lineage f WHERE f.task_id = t.task_id) AS files_touched\n FROM task_outcomes t${where}\n ORDER BY COALESCE(t.started_at, '') DESC LIMIT ?`,\n )\n .all(...params) as Array<Record<string, string | number | null>>;\n return rows.map((row) => ({\n taskId: String(row.task_id),\n runId: String(row.run_id),\n boardId: String(row.board_id),\n sessionId: String(row.session_id),\n agentId: String(row.agent_id),\n status: String(row.status),\n startedAt: row.started_at === null ? null : String(row.started_at),\n endedAt: row.ended_at === null ? null : String(row.ended_at),\n durationMs: row.duration_ms === null ? null : Number(row.duration_ms),\n retries: Number(row.retries),\n verificationFailures: Number(row.verification_failures),\n filesTouched: Number(row.files_touched),\n }));\n }\n\n fileLineage(\n options: {\n path?: string;\n paths?: string[];\n latestPerPath?: boolean;\n taskId?: string;\n boardId?: string;\n sessionId?: string;\n limit?: number;\n } = {},\n ): ChronicleFileLineageRow[] {\n const clauses: string[] = [];\n const params: Array<string | number> = [];\n if (options.path) {\n clauses.push('path_key = ?');\n params.push(normalizePathKey(options.path));\n }\n if (options.paths) {\n const pathKeys = [...new Set(options.paths.map(normalizePathKey))];\n if (pathKeys.length === 0) return [];\n clauses.push(`path_key IN (${pathKeys.map(() => '?').join(',')})`);\n params.push(...pathKeys);\n }\n if (options.taskId) {\n clauses.push('task_id = ?');\n params.push(options.taskId);\n }\n if (options.boardId) {\n clauses.push('board_id = ?');\n params.push(options.boardId);\n }\n if (options.sessionId) {\n clauses.push('session_id = ?');\n params.push(options.sessionId);\n }\n const where = clauses.length > 0 ? ` WHERE ${clauses.join(' AND ')}` : '';\n params.push(clampLimit(options.limit, 200));\n const projection =\n `path, operation, occurred_at, session_id, agent_id, task_id, board_id, run_id,\n tool_name, provider_id, model_id, source`;\n const sql = options.latestPerPath\n ? `SELECT ${projection} FROM (\n SELECT ${projection}, ROW_NUMBER() OVER (\n PARTITION BY path_key ORDER BY occurred_at DESC, event_id DESC\n ) AS path_rank\n FROM file_lineage${where}\n ) WHERE path_rank = 1 ORDER BY occurred_at DESC LIMIT ?`\n : `SELECT ${projection}\n FROM file_lineage${where} ORDER BY occurred_at DESC LIMIT ?`;\n const rows = this.db\n .prepare(sql)\n .all(...params) as Array<Record<string, string>>;\n return rows.map((row) => ({\n path: row.path!,\n operation: row.operation!,\n occurredAt: row.occurred_at!,\n sessionId: row.session_id!,\n agentId: row.agent_id!,\n taskId: row.task_id!,\n boardId: row.board_id!,\n runId: row.run_id!,\n toolName: row.tool_name!,\n providerId: row.provider_id!,\n modelId: row.model_id!,\n source: row.source!,\n }));\n }\n\n summary(): ChronicleMetricsSummary {\n const provider = this.db\n .prepare(\n 'SELECT COALESCE(SUM(attempts),0) a, COALESCE(SUM(completed),0) c, COALESCE(SUM(failed),0) f FROM provider_daily',\n )\n .get() as { a: number; c: number; f: number };\n const tasks: Record<string, number> = {};\n for (const row of this.db\n .prepare('SELECT status, COUNT(*) n FROM task_outcomes GROUP BY status')\n .all() as Array<{ status: string; n: number }>) {\n tasks[row.status] = Number(row.n);\n }\n const files = this.db\n .prepare('SELECT COUNT(*) n, COUNT(DISTINCT path) p FROM file_lineage')\n .get() as { n: number; p: number };\n const cost = this.db.prepare('SELECT COALESCE(SUM(cost),0) c FROM token_cost').get() as {\n c: number;\n };\n const terminal = Number(provider.c) + Number(provider.f);\n return {\n providers: {\n attempts: Number(provider.a),\n completed: Number(provider.c),\n failed: Number(provider.f),\n successRate: terminal > 0 ? Number(provider.c) / terminal : 0,\n },\n tasks,\n files: { mutations: Number(files.n), uniquePaths: Number(files.p) },\n estimatedCostUsd: Number(cost.c),\n };\n }\n\n /**\n * A `ChronicleSummary` for the default/unfiltered dashboard view \u2014 only\n * `from`/`to` (day-precision) narrow it. Any other ad hoc filter (text,\n * path, provider, model, session) can't be answered from these\n * fixed-dimension aggregates; callers must fall back to query.ts's\n * raw-scan summary for those.\n */\n defaultSummary(options: { from?: string; to?: string } = {}): ChronicleSummary {\n const fromDay = options.from?.slice(0, 10);\n const toDay = options.to?.slice(0, 10);\n const dayFilter = (column: string): { where: string; params: string[] } => {\n const clauses: string[] = [];\n const params: string[] = [];\n if (fromDay) { clauses.push(`${column} >= ?`); params.push(fromDay); }\n if (toDay) { clauses.push(`${column} <= ?`); params.push(toDay); }\n return { where: clauses.length > 0 ? ` WHERE ${clauses.join(' AND ')}` : '', params };\n };\n\n const providerRange = dayFilter('day');\n const provider = this.db\n .prepare(\n `SELECT COALESCE(SUM(attempts),0) attempts, COALESCE(SUM(completed),0) completed, COALESCE(SUM(failed),0) failed,\n COALESCE(SUM(retries),0) retries, COALESCE(SUM(fallbacks),0) fallbacks,\n COUNT(DISTINCT provider_id) providers, COUNT(DISTINCT model_id) models,\n COALESCE(SUM(input_tokens),0) inputTokens, COALESCE(SUM(output_tokens),0) outputTokens,\n COALESCE(SUM(cache_read_tokens),0) cacheReadTokens, COALESCE(SUM(cache_write_tokens),0) cacheWriteTokens,\n COALESCE(SUM(duration_ms_total),0) durationTotal, COALESCE(MAX(duration_ms_max),0) durationMax,\n COALESCE(SUM(duration_count),0) durationCount\n FROM provider_daily${providerRange.where}`,\n )\n .get(...providerRange.params) as Record<string, number>;\n\n const counterRange = dayFilter('day');\n const counters = this.db\n .prepare(\n `SELECT COALESCE(SUM(tool_calls),0) toolCalls, COALESCE(SUM(completed_tools),0) completedTools,\n COALESCE(SUM(failed_tools),0) failedTools, COALESCE(SUM(tool_duration_ms_total),0) toolDurationTotal,\n COALESCE(SUM(tool_duration_count),0) toolDurationCount, COALESCE(SUM(processes),0) processes,\n COALESCE(SUM(failed_processes),0) failedProcesses, COALESCE(SUM(file_events_all),0) fileEvents,\n COALESCE(SUM(decisions),0) decisions, COALESCE(SUM(escalations),0) escalations,\n COALESCE(SUM(agent_events),0) agentEvents, COALESCE(SUM(failures),0) failures,\n COALESCE(SUM(cancellations),0) cancellations\n FROM daily_counters${counterRange.where}`,\n )\n .get(...counterRange.params) as Record<string, number>;\n\n const familyRange = dayFilter('day');\n const familyRows = this.db\n .prepare(`SELECT family, count, failure_count FROM family_daily${familyRange.where}`)\n .all(...familyRange.params) as Array<{ family: string; count: number; failure_count: number }>;\n const families = { ...EMPTY_FAMILIES };\n const failuresByFamily = { ...EMPTY_FAMILIES };\n for (const row of familyRows) {\n const family = row.family as ChronicleSignalFamily;\n families[family] = Number(row.count);\n failuresByFamily[family] = Number(row.failure_count);\n }\n\n const agentRange = dayFilter('day');\n const uniqueAgents = (\n this.db.prepare(`SELECT COUNT(DISTINCT agent_id) n FROM agent_daily${agentRange.where}`).get(...agentRange.params) as { n: number }\n ).n;\n const requestRange = dayFilter('day');\n const logicalRequests = (\n this.db.prepare(`SELECT COUNT(DISTINCT logical_request_id) n FROM logical_request_daily${requestRange.where}`).get(...requestRange.params) as { n: number }\n ).n;\n const fileRange = dayFilter('day');\n const uniqueFiles = (\n this.db.prepare(`SELECT COUNT(DISTINCT path_key) n FROM file_seen_daily${fileRange.where}`).get(...fileRange.params) as { n: number }\n ).n;\n const costRange = dayFilter('day');\n const cost = (\n this.db.prepare(`SELECT COALESCE(SUM(cost),0) c FROM token_cost${costRange.where}`).get(...costRange.params) as { c: number }\n ).c;\n\n return {\n logicalRequests: Number(logicalRequests),\n modelAttempts: Number(provider.attempts),\n completedAttempts: Number(provider.completed),\n failedAttempts: Number(provider.failed),\n scheduledRetries: Number(provider.retries),\n fallbacks: Number(provider.fallbacks),\n providers: Number(provider.providers),\n models: Number(provider.models),\n inputTokens: Number(provider.inputTokens),\n outputTokens: Number(provider.outputTokens),\n cacheReadTokens: Number(provider.cacheReadTokens),\n cacheWriteTokens: Number(provider.cacheWriteTokens),\n estimatedCostUsd: Number(cost),\n providerAvgDurationMs: Number(provider.durationCount) > 0 ? Number(provider.durationTotal) / Number(provider.durationCount) : 0,\n // True p95 needs a retained distribution; this per-day aggregate only\n // keeps sum/max/count, so approximate with the observed max rather\n // than adding a per-attempt histogram write (would add the same kind\n // of per-event overhead this whole effort is trying to remove).\n providerP95DurationMs: Number(provider.durationMax),\n toolCalls: Number(counters.toolCalls),\n completedTools: Number(counters.completedTools),\n failedTools: Number(counters.failedTools),\n toolAvgDurationMs: Number(counters.toolDurationCount) > 0 ? Number(counters.toolDurationTotal) / Number(counters.toolDurationCount) : 0,\n processes: Number(counters.processes),\n failedProcesses: Number(counters.failedProcesses),\n fileEvents: Number(counters.fileEvents),\n uniqueFiles: Number(uniqueFiles),\n agentEvents: Number(counters.agentEvents),\n uniqueAgents: Number(uniqueAgents),\n decisions: Number(counters.decisions),\n escalations: Number(counters.escalations),\n failures: Number(counters.failures),\n cancellations: Number(counters.cancellations),\n families,\n failuresByFamily,\n };\n }\n\n // \u2500\u2500\u2500 Ingest internals \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n private ensureSchema(): void {\n const version = (this.db.prepare('PRAGMA user_version').get() as { user_version: number })\n .user_version;\n if (version !== 0 && version !== SCHEMA_VERSION) {\n // Derived cache \u2014 drop and re-ingest from whatever journal remains.\n this.db.exec(\n 'DROP TABLE IF EXISTS ingest_state; DROP TABLE IF EXISTS provider_daily;' +\n 'DROP TABLE IF EXISTS task_outcomes; DROP TABLE IF EXISTS file_lineage;' +\n 'DROP TABLE IF EXISTS token_cost; DROP TABLE IF EXISTS daily_counters;' +\n 'DROP TABLE IF EXISTS family_daily; DROP TABLE IF EXISTS agent_daily;' +\n 'DROP TABLE IF EXISTS logical_request_daily; DROP TABLE IF EXISTS file_seen_daily;',\n );\n }\n this.db.exec(`\n CREATE TABLE IF NOT EXISTS ingest_state (\n file TEXT PRIMARY KEY,\n bytes INTEGER NOT NULL\n );\n CREATE TABLE IF NOT EXISTS provider_daily (\n day TEXT NOT NULL,\n provider_id TEXT NOT NULL,\n model_id TEXT NOT NULL,\n attempts INTEGER NOT NULL DEFAULT 0,\n completed INTEGER NOT NULL DEFAULT 0,\n failed INTEGER NOT NULL DEFAULT 0,\n retries INTEGER NOT NULL DEFAULT 0,\n fallbacks INTEGER NOT NULL DEFAULT 0,\n input_tokens INTEGER NOT NULL DEFAULT 0,\n output_tokens INTEGER NOT NULL DEFAULT 0,\n cache_read_tokens INTEGER NOT NULL DEFAULT 0,\n cache_write_tokens INTEGER NOT NULL DEFAULT 0,\n duration_ms_total REAL NOT NULL DEFAULT 0,\n duration_ms_max REAL NOT NULL DEFAULT 0,\n duration_count INTEGER NOT NULL DEFAULT 0,\n PRIMARY KEY (day, provider_id, model_id)\n );\n CREATE TABLE IF NOT EXISTS task_outcomes (\n task_id TEXT PRIMARY KEY,\n run_id TEXT NOT NULL DEFAULT '',\n board_id TEXT NOT NULL DEFAULT '',\n session_id TEXT NOT NULL DEFAULT '',\n agent_id TEXT NOT NULL DEFAULT '',\n status TEXT NOT NULL DEFAULT 'started',\n started_at TEXT,\n ended_at TEXT,\n duration_ms REAL,\n retries INTEGER NOT NULL DEFAULT 0,\n verification_failures INTEGER NOT NULL DEFAULT 0\n );\n CREATE TABLE IF NOT EXISTS file_lineage (\n event_id TEXT PRIMARY KEY,\n path TEXT NOT NULL,\n path_key TEXT NOT NULL,\n operation TEXT NOT NULL,\n occurred_at TEXT NOT NULL,\n session_id TEXT NOT NULL DEFAULT '',\n agent_id TEXT NOT NULL DEFAULT '',\n task_id TEXT NOT NULL DEFAULT '',\n board_id TEXT NOT NULL DEFAULT '',\n run_id TEXT NOT NULL DEFAULT '',\n tool_name TEXT NOT NULL DEFAULT '',\n provider_id TEXT NOT NULL DEFAULT '',\n model_id TEXT NOT NULL DEFAULT '',\n source TEXT NOT NULL DEFAULT ''\n );\n -- Lookups filter on the case-normalized path_key (matching the query\n -- engine); the path column retains original casing for display.\n CREATE INDEX IF NOT EXISTS idx_file_lineage_path ON file_lineage(path_key, occurred_at);\n CREATE INDEX IF NOT EXISTS idx_file_lineage_task ON file_lineage(task_id);\n CREATE TABLE IF NOT EXISTS token_cost (\n scope_key TEXT PRIMARY KEY,\n day TEXT NOT NULL,\n occurred_at TEXT NOT NULL,\n sequence INTEGER NOT NULL,\n cost REAL NOT NULL\n );\n -- Backing store for defaultSummary(): per-day scalar counters plus\n -- dedup sets, populated for every ingested event (not just the\n -- provider/task/file families above).\n CREATE TABLE IF NOT EXISTS daily_counters (\n day TEXT PRIMARY KEY,\n tool_calls INTEGER NOT NULL DEFAULT 0,\n completed_tools INTEGER NOT NULL DEFAULT 0,\n failed_tools INTEGER NOT NULL DEFAULT 0,\n tool_duration_ms_total REAL NOT NULL DEFAULT 0,\n tool_duration_ms_max REAL NOT NULL DEFAULT 0,\n tool_duration_count INTEGER NOT NULL DEFAULT 0,\n processes INTEGER NOT NULL DEFAULT 0,\n failed_processes INTEGER NOT NULL DEFAULT 0,\n file_events_all INTEGER NOT NULL DEFAULT 0,\n decisions INTEGER NOT NULL DEFAULT 0,\n escalations INTEGER NOT NULL DEFAULT 0,\n agent_events INTEGER NOT NULL DEFAULT 0,\n failures INTEGER NOT NULL DEFAULT 0,\n cancellations INTEGER NOT NULL DEFAULT 0\n );\n CREATE TABLE IF NOT EXISTS family_daily (\n day TEXT NOT NULL,\n family TEXT NOT NULL,\n count INTEGER NOT NULL DEFAULT 0,\n failure_count INTEGER NOT NULL DEFAULT 0,\n PRIMARY KEY (day, family)\n );\n CREATE TABLE IF NOT EXISTS agent_daily (day TEXT NOT NULL, agent_id TEXT NOT NULL, PRIMARY KEY (day, agent_id));\n CREATE TABLE IF NOT EXISTS logical_request_daily (day TEXT NOT NULL, logical_request_id TEXT NOT NULL, PRIMARY KEY (day, logical_request_id));\n CREATE TABLE IF NOT EXISTS file_seen_daily (day TEXT NOT NULL, path_key TEXT NOT NULL, PRIMARY KEY (day, path_key));\n PRAGMA user_version = ${SCHEMA_VERSION};\n `);\n }\n\n private loadOffsets(): Map<string, number> {\n const rows = this.db.prepare('SELECT file, bytes FROM ingest_state').all() as Array<{\n file: string;\n bytes: number;\n }>;\n return new Map(rows.map((row) => [row.file, Number(row.bytes)]));\n }\n\n private pruneOffsets(existingFiles: string[]): void {\n const keep = new Set(\n existingFiles.map((file) => normalizeKey(path.relative(this.directory, file))),\n );\n for (const row of this.db.prepare('SELECT file FROM ingest_state').all() as Array<{\n file: string;\n }>) {\n if (!keep.has(row.file))\n this.db.prepare('DELETE FROM ingest_state WHERE file = ?').run(row.file);\n }\n }\n\n /** Read complete lines appended after `consumed` bytes. The trailing\n * partial line of an actively-written partition is left for the next\n * refresh \u2014 `ingest_state.bytes` only ever advances past full lines. */\n private async ingestFile(\n file: string,\n key: string,\n consumed: number,\n result: ChronicleMetricsRefreshResult,\n ): Promise<boolean> {\n let handle: fs.FileHandle;\n try {\n handle = await fs.open(file, 'r');\n } catch {\n return false;\n }\n try {\n const size = (await handle.stat()).size;\n if (size <= consumed) return false;\n let position = consumed;\n let remainder = Buffer.alloc(0);\n let advanced = consumed;\n this.db.exec('BEGIN');\n try {\n while (position < size) {\n const length = Math.min(READ_CHUNK_BYTES, size - position);\n const buffer = Buffer.allocUnsafe(length);\n const { bytesRead } = await handle.read(buffer, 0, length, position);\n if (bytesRead <= 0) break;\n position += bytesRead;\n const data =\n remainder.length > 0\n ? Buffer.concat([remainder, buffer.subarray(0, bytesRead)])\n : buffer.subarray(0, bytesRead);\n const lastNewline = data.lastIndexOf(0x0a);\n if (lastNewline < 0) {\n remainder = Buffer.from(data);\n continue;\n }\n // '\\n' is a single byte in UTF-8, so complete-line slices always\n // fall on character boundaries.\n for (const line of data.subarray(0, lastNewline).toString('utf8').split('\\n')) {\n const trimmed = line.trim();\n if (!trimmed) continue;\n try {\n this.ingestEvent(JSON.parse(trimmed) as ChronicleEvent);\n result.ingestedEvents++;\n } catch {\n result.invalidLines++;\n }\n }\n // `data` always begins at absolute offset `advanced` (remainder is\n // exactly the unconsumed bytes), so the newline index maps directly.\n advanced += lastNewline + 1;\n remainder = Buffer.from(data.subarray(lastNewline + 1));\n }\n this.db\n .prepare(\n 'INSERT INTO ingest_state (file, bytes) VALUES (?, ?) ' +\n 'ON CONFLICT(file) DO UPDATE SET bytes = excluded.bytes',\n )\n .run(key, advanced);\n this.db.exec('COMMIT');\n } catch (error) {\n this.db.exec('ROLLBACK');\n throw error;\n }\n result.ingestedBytes += advanced - consumed;\n return advanced > consumed;\n } finally {\n await handle.close();\n }\n }\n\n private ingestEvent(event: ChronicleEvent): void {\n if (typeof event?.eventType !== 'string' || !event.scope) return;\n this.ingestDailyCounters(event);\n const type = event.eventType;\n if (type.startsWith('provider.attempt.') || type === 'provider.fallback') {\n this.ingestProvider(event);\n } else if (type === 'token.accounted') {\n this.ingestTokenCost(event);\n } else if (/^(?:sdd|subagent|kanban)\\.task[._]/.test(type)) {\n this.ingestTask(event);\n } else if (type === 'file.event' || /^file\\.(?:tool|external)\\./.test(type)) {\n this.ingestFileEvent(event);\n }\n }\n\n /** Runs for every ingested event (not just the type-specific branches\n * below) \u2014 mirrors query.ts's updateSummary() closely enough that\n * defaultSummary() matches what a raw scan of the same window would say. */\n private ingestDailyCounters(event: ChronicleEvent): void {\n const day = eventDay(event);\n this.db.prepare('INSERT OR IGNORE INTO daily_counters (day) VALUES (?)').run(day);\n const bump = (sql: string, ...params: Array<string | number>) =>\n this.db.prepare(`UPDATE daily_counters SET ${sql} WHERE day = ?`).run(...params, day);\n\n const family = signalFamily(event);\n const failed = isTerminalFailure(event) ? 1 : 0;\n this.db\n .prepare(\n `INSERT INTO family_daily (day, family, count, failure_count) VALUES (?, ?, 1, ?)\n ON CONFLICT(day, family) DO UPDATE SET count = count + 1, failure_count = failure_count + excluded.failure_count`,\n )\n .run(day, family, failed);\n if (failed) bump('failures = failures + 1');\n if (event.outcome === 'cancelled' || event.outcome === 'abandoned') bump('cancellations = cancellations + 1');\n if (family === 'agent') bump('agent_events = agent_events + 1');\n\n if (event.correlation.logicalRequestId) {\n this.db\n .prepare('INSERT OR IGNORE INTO logical_request_daily (day, logical_request_id) VALUES (?, ?)')\n .run(day, event.correlation.logicalRequestId);\n }\n if (event.scope.agentId) {\n this.db.prepare('INSERT OR IGNORE INTO agent_daily (day, agent_id) VALUES (?, ?)').run(day, event.scope.agentId);\n }\n\n const type = event.eventType;\n if (type === 'decision.requested') bump('decisions = decisions + 1');\n else if (type === 'decision.escalated') bump('escalations = escalations + 1');\n else if (type === 'tool.started') bump('tool_calls = tool_calls + 1');\n else if (type === 'tool.executed' || type === 'tool.failed') {\n const dur = durationMs(event);\n const durationCount = dur > 0 ? 1 : 0;\n bump(\n `${type === 'tool.executed' ? 'completed_tools' : 'failed_tools'} = ${type === 'tool.executed' ? 'completed_tools' : 'failed_tools'} + 1,\n tool_duration_ms_total = tool_duration_ms_total + ?, tool_duration_ms_max = MAX(tool_duration_ms_max, ?), tool_duration_count = tool_duration_count + ?`,\n dur, dur, durationCount,\n );\n } else if (type === 'process.started') bump('processes = processes + 1');\n else if (type === 'process.completed' && event.outcome === 'failure') bump('failed_processes = failed_processes + 1');\n\n if (event.resource?.kind === 'file' || type.startsWith('file.')) {\n bump('file_events_all = file_events_all + 1');\n if (event.resource?.path) {\n this.db\n .prepare('INSERT OR IGNORE INTO file_seen_daily (day, path_key) VALUES (?, ?)')\n .run(day, normalizePathKey(event.resource.path));\n }\n }\n }\n\n private ingestProvider(event: ChronicleEvent): void {\n const day = eventDay(event);\n // provider.fallback carries no top-level runtime identity \u2014 it belongs to\n // the provider being fallen back FROM, held in attributes.from. Attribute\n // it there rather than letting it manufacture a phantom ('', '') row.\n const providerId =\n event.runtime?.providerId ?? asString(readPath(event.attributes ?? {}, 'from.providerId')) ?? '';\n const modelId =\n event.runtime?.modelId ?? asString(readPath(event.attributes ?? {}, 'from.model')) ?? '';\n // No identity at all \u2192 not attributable to any provider row; skip.\n if (!providerId && !modelId) return;\n this.db\n .prepare('INSERT OR IGNORE INTO provider_daily (day, provider_id, model_id) VALUES (?, ?, ?)')\n .run(day, providerId, modelId);\n const update = (sql: string, ...params: Array<string | number>) =>\n this.db\n .prepare(\n `UPDATE provider_daily SET ${sql} WHERE day = ? AND provider_id = ? AND model_id = ?`,\n )\n .run(...params, day, providerId, modelId);\n const duration = durationMs(event);\n switch (event.eventType) {\n case 'provider.attempt.started':\n update('attempts = attempts + 1');\n break;\n case 'provider.attempt.completed':\n update(\n 'completed = completed + 1, input_tokens = input_tokens + ?, output_tokens = output_tokens + ?, ' +\n 'cache_read_tokens = cache_read_tokens + ?, cache_write_tokens = cache_write_tokens + ?, ' +\n 'duration_ms_total = duration_ms_total + ?, duration_ms_max = MAX(duration_ms_max, ?), ' +\n 'duration_count = duration_count + ?',\n numberAt(event, 'usage.input'),\n numberAt(event, 'usage.output'),\n numberAt(event, 'usage.cacheRead'),\n numberAt(event, 'usage.cacheWrite'),\n duration,\n duration,\n duration > 0 ? 1 : 0,\n );\n break;\n case 'provider.attempt.failed':\n update(\n 'failed = failed + 1, retries = retries + ?, duration_ms_total = duration_ms_total + ?, ' +\n 'duration_ms_max = MAX(duration_ms_max, ?), duration_count = duration_count + ?',\n event.attributes?.retryScheduled === true ? 1 : 0,\n duration,\n duration,\n duration > 0 ? 1 : 0,\n );\n break;\n case 'provider.fallback':\n update('fallbacks = fallbacks + 1');\n break;\n default:\n break;\n }\n }\n\n private ingestTokenCost(event: ChronicleEvent): void {\n const cost = readPath(event.attributes ?? {}, 'cost.total');\n if (typeof cost !== 'number' || !Number.isFinite(cost)) return;\n const scopeKey = `${event.scope.projectId ?? ''}\\0${event.scope.sessionId ?? ''}\\0${event.scope.agentId ?? ''}`;\n const occurredAt = event.occurredAt ?? event.observedAt;\n // Latest-wins per scope: token.accounted carries a cumulative snapshot.\n this.db\n .prepare(\n `INSERT INTO token_cost (scope_key, day, occurred_at, sequence, cost) VALUES (?, ?, ?, ?, ?)\n ON CONFLICT(scope_key) DO UPDATE SET\n day = excluded.day, occurred_at = excluded.occurred_at,\n sequence = excluded.sequence, cost = excluded.cost\n WHERE excluded.occurred_at > token_cost.occurred_at\n OR (excluded.occurred_at = token_cost.occurred_at AND excluded.sequence > token_cost.sequence)`,\n )\n .run(scopeKey, eventDay(event), occurredAt, event.sequence, cost);\n }\n\n private ingestTask(event: ChronicleEvent): void {\n const attributes = event.attributes ?? {};\n const taskId = event.scope.taskId ?? stringAt(attributes, 'taskId');\n if (!taskId) return;\n const occurredAt = event.occurredAt ?? event.observedAt;\n this.db.prepare('INSERT OR IGNORE INTO task_outcomes (task_id) VALUES (?)').run(taskId);\n const set = (sql: string, ...params: Array<string | number>) =>\n this.db.prepare(`UPDATE task_outcomes SET ${sql} WHERE task_id = ?`).run(...params, taskId);\n // Lineage columns: last non-empty observation wins.\n const lineage: Array<[string, string | undefined]> = [\n ['run_id', stringAt(attributes, 'runId')],\n ['board_id', event.scope.kanbanBoardId ?? stringAt(attributes, 'boardId')],\n ['session_id', event.scope.sessionId],\n ['agent_id', event.scope.agentId ?? stringAt(attributes, 'subagentId')],\n ];\n for (const [column, value] of lineage) {\n if (value) set(`${column} = ?`, value);\n }\n const base = event.eventType.replace(/^(?:sdd|subagent|kanban)\\.task[._]/, '');\n switch (base) {\n case 'started':\n set(\"status = 'started', started_at = COALESCE(started_at, ?)\", occurredAt);\n break;\n case 'completed':\n set(\n \"status = 'completed', ended_at = ?, duration_ms = ?\",\n occurredAt,\n numberOrDuration(event, attributes),\n );\n break;\n case 'failed':\n set(\"status = 'failed', ended_at = ?\", occurredAt);\n break;\n case 'retrying':\n set('retries = retries + 1');\n break;\n case 'verification_failed':\n set('verification_failures = verification_failures + 1');\n break;\n case 'merged':\n set(\"status = 'merged'\");\n break;\n case 'conflict':\n set(\"status = 'conflict'\");\n break;\n default:\n break;\n }\n }\n\n private ingestFileEvent(event: ChronicleEvent): void {\n const attributes = event.attributes ?? {};\n const operation = stringAt(attributes, 'operation') ?? '';\n if (!operation || operation === 'read') return;\n const filePath = event.resource?.path ?? stringAt(attributes, 'filePath');\n if (!filePath) return;\n this.db\n .prepare(\n `INSERT OR IGNORE INTO file_lineage\n (event_id, path, path_key, operation, occurred_at, session_id, agent_id, task_id, board_id, run_id,\n tool_name, provider_id, model_id, source)\n VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`,\n )\n .run(\n event.eventId,\n normalizeKey(filePath),\n normalizePathKey(filePath),\n operation,\n event.occurredAt ?? event.observedAt,\n event.scope.sessionId ?? '',\n event.scope.agentId ?? '',\n event.scope.taskId ?? stringAt(attributes, 'taskId') ?? '',\n event.scope.kanbanBoardId ?? stringAt(attributes, 'boardId') ?? '',\n stringAt(attributes, 'runId') ?? '',\n stringAt(attributes, 'toolName') ?? '',\n event.runtime?.providerId ?? stringAt(attributes, 'provider') ?? '',\n event.runtime?.modelId ?? stringAt(attributes, 'model') ?? '',\n stringAt(attributes, 'source') ?? (event.eventType === 'file.event' ? 'tool' : 'external'),\n );\n }\n}\n\n// \u2500\u2500\u2500 Helpers \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nfunction eventDay(event: ChronicleEvent): string {\n return (event.occurredAt ?? event.observedAt).slice(0, 10);\n}\n\nfunction durationMs(event: ChronicleEvent): number {\n const value = Number(event.durationNs ?? 0) / 1_000_000;\n return Number.isFinite(value) && value > 0 ? value : 0;\n}\n\nfunction numberOrDuration(event: ChronicleEvent, attributes: Record<string, unknown>): number {\n const explicit = attributes.durationMs;\n if (typeof explicit === 'number' && Number.isFinite(explicit)) return explicit;\n return durationMs(event);\n}\n\nfunction numberAt(event: ChronicleEvent, dotPath: string): number {\n const value = readPath(event.attributes ?? {}, dotPath);\n return typeof value === 'number' && Number.isFinite(value) ? value : 0;\n}\n\nfunction readPath(value: Record<string, unknown>, key: string): unknown {\n return key\n .split('.')\n .reduce<unknown>(\n (current, part) =>\n current && typeof current === 'object'\n ? (current as Record<string, unknown>)[part]\n : undefined,\n value,\n );\n}\n\nfunction stringAt(record: Record<string, unknown>, key: string): string | undefined {\n const value = record[key];\n return typeof value === 'string' && value.length > 0 ? value : undefined;\n}\n\nfunction asString(value: unknown): string | undefined {\n return typeof value === 'string' && value.length > 0 ? value : undefined;\n}\n\nfunction clampLimit(limit: number | undefined, fallback: number): number {\n if (typeof limit !== 'number' || !Number.isFinite(limit) || limit <= 0) return fallback;\n return Math.min(Math.floor(limit), 10_000);\n}\n\nfunction normalizeKey(value: string): string {\n return value.replaceAll('\\\\', '/');\n}\n\n/** Case-normalized path key for lineage lookups. Mirrors the query engine's\n * path comparison (lowercase + forward-slash) and additionally strips a\n * leading `./` so a repo-relative path matches however the tool reported it \u2014\n * case differences on Windows are the common mismatch. */\nfunction normalizePathKey(value: string): string {\n return value.replaceAll('\\\\', '/').replace(/^\\.\\//, '').toLowerCase();\n}\n", "const SQLITE_EXPERIMENTAL_WARNING_RE = /sqlite is an experimental feature/i;\n\nfunction isSqliteExperimentalWarning(warning: unknown, rest: readonly unknown[]): boolean {\n const message = typeof warning === 'string' ? warning : warning instanceof Error ? warning.message : '';\n const typeOrOptions = rest[0];\n const warningType =\n typeof warning === 'string'\n ? typeof typeOrOptions === 'string'\n ? typeOrOptions\n : typeof typeOrOptions === 'object' &&\n typeOrOptions !== null &&\n 'type' in typeOrOptions &&\n typeof typeOrOptions.type === 'string'\n ? typeOrOptions.type\n : ''\n : warning instanceof Error\n ? warning.name\n : '';\n const warningCode =\n typeof warning === 'string'\n ? typeof typeOrOptions === 'object' &&\n typeOrOptions !== null &&\n 'code' in typeOrOptions &&\n typeof typeOrOptions.code === 'string'\n ? typeOrOptions.code\n : typeof rest[1] === 'string'\n ? rest[1]\n : ''\n : warning instanceof Error && 'code' in warning && typeof warning.code === 'string'\n ? warning.code\n : '';\n\n return (\n SQLITE_EXPERIMENTAL_WARNING_RE.test(message) &&\n (warningType === 'ExperimentalWarning' || warningCode === 'ExperimentalWarning')\n );\n}\n\n/**\n * Run a synchronous `node:sqlite` load while filtering only Node's built-in\n * SQLite ExperimentalWarning. All other warnings still go through the original\n * process warning path, and the patch is removed before returning.\n */\nexport function withSqliteExperimentalWarningSuppressed<T>(run: () => T): T {\n const originalEmitWarning = process.emitWarning;\n const forwardWarning = originalEmitWarning.bind(process) as (\n warning: unknown,\n ...rest: unknown[]\n ) => void;\n\n process.emitWarning = ((warning: unknown, ...rest: unknown[]): void => {\n if (isSqliteExperimentalWarning(warning, rest)) return;\n forwardWarning(warning, ...rest);\n }) as typeof process.emitWarning;\n\n try {\n return run();\n } finally {\n process.emitWarning = originalEmitWarning;\n }\n}\n", "import { createHash } from 'node:crypto';\nimport { createReadStream } from 'node:fs';\nimport * as fs from 'node:fs/promises';\nimport * as path from 'node:path';\nimport { createInterface } from 'node:readline';\nimport { comparePartitionPaths, PARTITION_FILE_PATTERN } from './partition-filename.js';\nimport { type ChroniclePartitionRange, ChroniclePartitionRangeCache } from './partition-range-cache.js';\nimport type { ChronicleEvent, ChronicleOutcome, ChronicleResourceRef } from './types.js';\n\nexport interface ChronicleQuery {\n eventId?: string;\n eventTypes?: string[]; outcomes?: ChronicleOutcome[]; from?: string; to?: string;\n projectId?: string; sessionId?: string; agentId?: string; taskId?: string;\n providerId?: string; modelId?: string; traceId?: string; logicalRequestId?: string;\n attemptId?: string; toolCallId?: string; resourceKind?: ChronicleResourceRef['kind'];\n resourceId?: string; path?: string; line?: number; tags?: Record<string, string>;\n attributes?: Record<string, unknown>; text?: string; order?: 'asc' | 'desc';\n limit?: number; cursor?: string;\n}\n\nexport interface ChronicleQueryResult {\n events: ChronicleEvent[]; total: number; nextCursor?: string;\n scannedEvents: number; sourceFiles: number; invalidLines: number;\n summary: ChronicleSummary;\n}\n\n/** Derived once from all matching events; never from the paginated UI sample. */\nexport interface ChronicleSummary {\n logicalRequests: number; modelAttempts: number; completedAttempts: number; failedAttempts: number;\n scheduledRetries: number; fallbacks: number; providers: number; models: number;\n inputTokens: number; outputTokens: number; cacheReadTokens: number; cacheWriteTokens: number;\n estimatedCostUsd: number;\n providerAvgDurationMs: number; providerP95DurationMs: number;\n toolCalls: number; completedTools: number; failedTools: number; toolAvgDurationMs: number;\n processes: number; failedProcesses: number; fileEvents: number; uniqueFiles: number;\n agentEvents: number; uniqueAgents: number; decisions: number; escalations: number;\n failures: number; cancellations: number;\n families: Record<ChronicleSignalFamily, number>;\n failuresByFamily: Record<ChronicleSignalFamily, number>;\n}\nexport type ChronicleSignalFamily = 'llm'|'agent'|'tool'|'file'|'memory'|'task'|'decision'|'runtime'|'finding';\n\nexport type ChronicleFacet = 'eventType' | 'outcome' | 'projectId' | 'sessionId' |\n 'agentId' | 'taskId' | 'providerId' | 'modelId' | 'resourceKind' | 'resourcePath' | 'toolCallId';\nexport interface ChronicleFacetValue { value: string; count: number }\nexport type ChronicleFacetResults = Partial<Record<ChronicleFacet, ChronicleFacetValue[]>>;\n\n/**\n * The complete set of valid {@link ChronicleFacet} values. Shared by both\n * the CLI-embedded and standalone WebUI message routers so they can validate\n * `chronicle.facet` / `chronicle.facets` payloads against a single source of\n * truth \u2014 if `ChronicleFacet` grows a member, this set is the only place\n * that needs updating.\n */\nexport const CHRONICLE_FACET_FIELDS: ReadonlySet<ChronicleFacet> = new Set<ChronicleFacet>([\n 'eventType',\n 'outcome',\n 'projectId',\n 'sessionId',\n 'agentId',\n 'taskId',\n 'providerId',\n 'modelId',\n 'resourceKind',\n 'resourcePath',\n 'toolCallId',\n]);\nexport type ChronicleRelationKind = 'parent_span' | 'trace' | 'tool_call' | 'logical_request' |\n 'attempt' | 'decision' | 'network_request' | 'prompt_manifest' | 'resource_lineage';\nexport interface ChronicleGraphEdge { from: string; to: string; kind: ChronicleRelationKind; confidence: 'explicit' | 'correlated' | 'inferred' }\nexport interface ChronicleGraphResult { nodes: ChronicleEvent[]; edges: ChronicleGraphEdge[]; truncated: boolean }\n\ninterface ChronicleOrderKey {\n occurredAt: string;\n persistedAt: string;\n sequence: number;\n eventId: string;\n}\n\ninterface ChronicleSnapshotEntry {\n id: string;\n size: number;\n}\n\ninterface ChronicleCursor {\n version: 1;\n order: 'asc' | 'desc';\n queryHash: string;\n after: ChronicleOrderKey;\n snapshot: ChronicleSnapshotEntry[];\n}\n\ninterface SnapshotFile extends ChronicleSnapshotEntry {\n file: string;\n}\n\nconst MAX_CURSOR_SNAPSHOT_ENTRIES = 10_000;\n\n// \u2500\u2500 Streaming line-by-line reader \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nfunction streamLines(filePath: string, maxBytes?: number): AsyncIterableIterator<string> {\n const stream = createReadStream(filePath, {\n encoding: 'utf8',\n highWaterMark: 256 * 1024,\n ...(maxBytes !== undefined ? { end: maxBytes - 1 } : {}),\n });\n const rl = createInterface({ input: stream, crlfDelay: Infinity });\n return rl[Symbol.asyncIterator]() as AsyncIterableIterator<string>;\n}\n\n/** One dedicated full pass over a closed file to learn its true occurredAt bounds. */\nasync function computeOccurredAtRange(\n file: string,\n size: number,\n): Promise<{ min: string; max: string } | undefined> {\n let min: string | undefined;\n let max: string | undefined;\n for await (const line of streamLines(file, size)) {\n if (!line.trim()) continue;\n let event: ChronicleEvent;\n try {\n event = JSON.parse(line) as ChronicleEvent;\n if (!isChronicleEvent(event)) continue;\n } catch { continue; }\n const occurredAt = event.occurredAt ?? event.observedAt;\n if (min === undefined || occurredAt < min) min = occurredAt;\n if (max === undefined || occurredAt > max) max = occurredAt;\n }\n return min === undefined ? undefined : { min, max: max! };\n}\n\nfunction rangeOverlaps(range: ChroniclePartitionRange, query: ChronicleQuery): boolean {\n if (range.empty) return false;\n if (query.from && range.maxOccurredAt! < query.from) return false;\n if (query.to && range.minOccurredAt! > query.to) return false;\n return true;\n}\n\n// \u2500\u2500 Streaming query engine (no pre-loaded events) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n/** Queryable projection over immutable Chronicle JSONL partitions.\n * Events are streamed on demand \u2014 no full-file load into memory. */\nexport interface ChronicleQueryEngineOptions {\n /** Shared, longer-lived cache of closed partitions' observed occurredAt ranges. */\n rangeCache?: ChroniclePartitionRangeCache;\n}\n\nexport class ChronicleQueryEngine {\n private readonly partitionFiles: string[];\n private readonly rangeCache: ChroniclePartitionRangeCache | undefined;\n /** The one file (if any) that could still be actively appended to \u2014 never cache-checked or skipped. */\n private readonly activeFile: string | undefined;\n\n private constructor(\n files: string[],\n readonly diagnostics: { sourceFiles: number; invalidLines: number },\n rangeCache?: ChroniclePartitionRangeCache,\n activeFile?: string,\n ) {\n this.partitionFiles = files;\n this.rangeCache = rangeCache;\n this.activeFile = activeFile;\n }\n\n static async fromDirectory(\n directory: string,\n options?: ChronicleQueryEngineOptions,\n ): Promise<ChronicleQueryEngine> {\n const resolved = path.resolve(directory);\n const files = await findPartitions(resolved);\n const rangeCache = options?.rangeCache ?? new ChroniclePartitionRangeCache(resolved);\n return new ChronicleQueryEngine(\n files,\n { sourceFiles: files.length, invalidLines: 0 },\n rangeCache,\n files.at(-1),\n );\n }\n\n static async fromFiles(files: string[]): Promise<ChronicleQueryEngine> {\n return new ChronicleQueryEngine(files, { sourceFiles: files.length, invalidLines: 0 });\n }\n\n /**\n * Returns the file's observed (min, max) `occurredAt` range, computing and\n * caching it on first use. Only ever called for closed/immutable files\n * (never `this.activeFile`) \u2014 see the skip-check call sites.\n */\n private async getOrComputeRange(file: string, size: number): Promise<ChroniclePartitionRange> {\n const cached = await this.rangeCache!.get(file, size);\n if (cached) return cached;\n const computed = await computeOccurredAtRange(file, size);\n const range: ChroniclePartitionRange = computed\n ? { size, minOccurredAt: computed.min, maxOccurredAt: computed.max }\n : { size, empty: true };\n this.rangeCache!.set(file, range);\n return range;\n }\n\n /** True when a closed file's cached range provably cannot contain a match for `query`. */\n private async canSkip(file: string, size: number, query: ChronicleQuery): Promise<boolean> {\n if (!this.rangeCache || (!query.from && !query.to) || file === this.activeFile) return false;\n const range = await this.getOrComputeRange(file, size);\n return !rangeOverlaps(range, query);\n }\n\n /** Stream all partitions, filter, and return the requested page + summary. */\n async query(query: ChronicleQuery = {}): Promise<ChronicleQueryResult> {\n const order = query.order ?? 'desc';\n const limit = Math.max(1, Math.min(query.limit ?? 100, 10_000));\n const queryHash = hashQuery(query);\n const cursor = decodeCursor(query.cursor, order, queryHash);\n const snapshotFiles = cursor\n ? await resolveSnapshotFiles(this.partitionFiles, cursor.snapshot)\n : await captureSnapshot(this.partitionFiles);\n const files = order === 'asc' ? snapshotFiles : snapshotFiles.slice().reverse();\n const summaryAcc = createSummaryAccumulator();\n const orderedCandidates: ChronicleEvent[] = [];\n const pageOrder = (left: ChronicleEvent, right: ChronicleEvent) =>\n compareEvents(left, right) * (order === 'asc' ? 1 : -1);\n let totalCount = 0;\n let remainingCount = 0;\n let scannedEvents = 0;\n let invalidLines = 0;\n\n for (const snapshotFile of files) {\n try {\n if (snapshotFile.size === 0) continue;\n // A closed file whose observed occurredAt range can't overlap [from, to]\n // is skipped with zero I/O. scannedEvents/invalidLines below reflect\n // only lines actually read this call, so a skip legitimately lowers\n // them \u2014 that's the optimization working, not a regression.\n if (await this.canSkip(snapshotFile.file, snapshotFile.size, query)) continue;\n const lines = order === 'asc'\n ? streamLines(snapshotFile.file, snapshotFile.size)\n : reverseLines(snapshotFile.file, snapshotFile.size);\n\n for await (const line of lines) {\n if (!line.trim()) continue;\n let event: ChronicleEvent;\n try {\n event = JSON.parse(line) as ChronicleEvent;\n if (!isChronicleEvent(event)) { invalidLines++; continue; }\n } catch { invalidLines++; continue; }\n scannedEvents++;\n\n if (!matches(event, query)) continue;\n totalCount++;\n updateSummary(summaryAcc, event);\n\n if (cursor && compareEventToKey(event, cursor.after) * (order === 'asc' ? 1 : -1) <= 0) {\n continue;\n }\n remainingCount++;\n\n // Keyset pagination retains only this page's best `limit` matches.\n // Cursor depth and journal size therefore cannot grow page memory.\n const insertionIndex = findInsertionIndex(orderedCandidates, event, pageOrder);\n if (insertionIndex < limit) {\n orderedCandidates.splice(insertionIndex, 0, event);\n if (orderedCandidates.length > limit) orderedCandidates.pop();\n }\n }\n } catch {\n // Skip unreadable partitions\n }\n }\n\n const pageEvents = orderedCandidates;\n const lastEvent = pageEvents.at(-1);\n\n if (this.rangeCache) {\n this.rangeCache.prune(this.partitionFiles);\n await this.rangeCache.flush();\n }\n\n return {\n events: pageEvents,\n total: totalCount,\n summary: finalizeSummary(summaryAcc),\n ...(lastEvent && pageEvents.length < remainingCount\n ? { nextCursor: encodeCursor({\n version: 1,\n order,\n queryHash,\n after: orderKey(lastEvent),\n snapshot: snapshotFiles.map(({ id, size }) => ({ id, size })),\n }) } : {}),\n scannedEvents,\n sourceFiles: snapshotFiles.length,\n invalidLines,\n };\n }\n\n /** Stream all partitions once and compute value counts for every requested facet. */\n async facets(\n fields: readonly ChronicleFacet[],\n query: ChronicleQuery = {},\n limit = 100,\n ): Promise<ChronicleFacetResults> {\n const uniqueFields = [...new Set(fields)];\n if (uniqueFields.length === 0) return {};\n const counts = new Map(uniqueFields.map((field) => [field, new Map<string, number>()]));\n const snapshotFiles = await captureSnapshot(this.partitionFiles);\n let invalidLines = 0;\n for (const snapshotFile of snapshotFiles) {\n try {\n if (snapshotFile.size === 0) continue;\n if (await this.canSkip(snapshotFile.file, snapshotFile.size, query)) continue;\n for await (const line of streamLines(snapshotFile.file, snapshotFile.size)) {\n if (!line.trim()) continue;\n let event: ChronicleEvent;\n try {\n event = JSON.parse(line) as ChronicleEvent;\n if (!isChronicleEvent(event)) { invalidLines++; continue; }\n } catch { invalidLines++; continue; }\n if (!matches(event, query)) continue;\n for (const field of uniqueFields) {\n const value = facetValue(event, field);\n const fieldCounts = counts.get(field)!;\n if (value !== undefined) fieldCounts.set(value, (fieldCounts.get(value) ?? 0) + 1);\n }\n }\n } catch { /* skip unreadable */ }\n }\n this.diagnostics.invalidLines = invalidLines;\n if (this.rangeCache) {\n this.rangeCache.prune(this.partitionFiles);\n await this.rangeCache.flush();\n }\n const result: ChronicleFacetResults = {};\n for (const field of uniqueFields) {\n result[field] = [...counts.get(field)!]\n .map(([value, count]) => ({ value, count }))\n .sort((a, b) => b.count - a.count || a.value.localeCompare(b.value))\n .slice(0, Math.max(0, limit));\n }\n return result;\n }\n\n /** Stream all partitions and compute one facet's value counts. */\n async facet(field: ChronicleFacet, query: ChronicleQuery = {}, limit = 100): Promise<ChronicleFacetValue[]> {\n return (await this.facets([field], query, limit))[field] ?? [];\n }\n\n /** Expand explicit and typed correlation edges; temporal proximity alone never creates causality. */\n async graph(seed: ChronicleQuery = {}, hops = 2, maxNodes = 1_000): Promise<ChronicleGraphResult> {\n const nodeLimit = Math.max(0, Math.floor(maxNodes));\n const selected = new Map<string, ChronicleEvent>();\n let seedCount = 0;\n\n // Pass 1 retains only the bounded seed set.\n for await (const event of streamEvents(this.partitionFiles)) {\n if (!matches(event, seed)) continue;\n seedCount++;\n if (selected.size < nodeLimit) selected.set(event.eventId, event);\n }\n\n let frontier = [...selected.values()];\n const depthLimit = Math.max(0, Math.min(hops, 10));\n for (let depth = 0; depth < depthLimit && frontier.length > 0 && selected.size < nodeLimit; depth++) {\n const frontierKeys = new Set(frontier.flatMap((event) => relationKeys(event).map((relation) => relation.key)));\n const next: ChronicleEvent[] = [];\n\n // Each hop is another streaming pass. Only related nodes up to maxNodes\n // are retained, so journal size cannot determine graph memory usage.\n for await (const event of streamEvents(this.partitionFiles)) {\n if (selected.has(event.eventId)) continue;\n if (!relationKeys(event).some((relation) => frontierKeys.has(relation.key))) continue;\n selected.set(event.eventId, event);\n next.push(event);\n if (selected.size >= nodeLimit) break;\n }\n frontier = next;\n }\n\n const nodes = [...selected.values()].sort(compareEvents);\n const byKey = new Map<string, ChronicleEvent[]>();\n for (const node of nodes) for (const relation of relationKeys(node)) {\n const related = byKey.get(relation.key) ?? [];\n related.push(node);\n byKey.set(relation.key, related);\n }\n\n const edges: ChronicleGraphEdge[] = [];\n const seen = new Set<string>();\n for (const node of nodes) for (const relation of relationKeys(node)) for (const candidate of byKey.get(relation.key) ?? []) {\n if (candidate.eventId === node.eventId) continue;\n const [from, to] = compareEvents(node, candidate) <= 0 ? [node, candidate] : [candidate, node];\n const id = `${from.eventId}:${to.eventId}:${relation.kind}`;\n if (!seen.has(id)) { seen.add(id); edges.push({ from: from.eventId, to: to.eventId, kind: relation.kind, confidence: relation.confidence }); }\n }\n return { nodes, edges, truncated: seedCount > nodeLimit || selected.size >= nodeLimit };\n }\n}\n\nasync function* streamEvents(files: readonly string[]): AsyncGenerator<ChronicleEvent> {\n for (const file of files) {\n try {\n for await (const line of streamLines(file)) {\n if (!line.trim()) continue;\n try {\n const event = JSON.parse(line) as ChronicleEvent;\n if (isChronicleEvent(event)) yield event;\n } catch { /* skip invalid lines */ }\n }\n } catch { /* skip unreadable partitions */ }\n }\n}\n\n// \u2500\u2500 Reverse line reader (reads a file from end to start) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function* reverseLines(filePath: string, maxBytes?: number): AsyncGenerator<string> {\n const CHUNK = 64 * 1024;\n const NEWLINE = 0x0a;\n let handle: fs.FileHandle;\n try { handle = await fs.open(filePath, 'r'); } catch { return; }\n try {\n const fileSize = (await handle.stat()).size;\n const size = Math.min(fileSize, maxBytes ?? fileSize);\n let position = size;\n let suffix = Buffer.alloc(0);\n while (position > 0) {\n const length = Math.min(CHUNK, position);\n position -= length;\n const buffer = Buffer.allocUnsafe(length);\n await handle.read(buffer, 0, length, position);\n const data = suffix.length === 0 ? buffer : Buffer.concat([buffer, suffix]);\n let lineEnd = data.length;\n let firstNewline = -1;\n for (let index = data.length - 1; index >= 0; index--) {\n if (data[index] !== NEWLINE) continue;\n const trimmed = data.subarray(index + 1, lineEnd).toString('utf8').trim();\n if (trimmed) yield trimmed;\n lineEnd = index;\n firstNewline = index;\n }\n suffix = firstNewline >= 0 ? Buffer.from(data.subarray(0, firstNewline)) : data;\n }\n const trimmed = suffix.toString('utf8').trim();\n if (trimmed) yield trimmed;\n } finally { await handle.close(); }\n}\n\n// \u2500\u2500 Running summary accumulator (replaces scan-then-summarize) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport interface SummaryAcc {\n logicalRequestIds: Set<string>;\n modelAttempts: number; completedAttempts: number; failedAttempts: number;\n scheduledRetries: number; fallbacks: number;\n providers: Set<string>; models: Set<string>;\n inputTokens: number; outputTokens: number;\n cacheReadTokens: number; cacheWriteTokens: number;\n costByScope: Map<string, { cost: number; event: ChronicleEvent }>;\n providerDurations: number[];\n toolCalls: number; completedTools: number; failedTools: number;\n toolDurations: number[];\n processes: number; failedProcesses: number;\n fileEvents: number; uniqueFiles: Set<string>;\n agentEvents: number; uniqueAgents: Set<string>;\n decisions: number; escalations: number;\n failures: number; cancellations: number;\n families: Record<ChronicleSignalFamily, number>;\n failuresByFamily: Record<ChronicleSignalFamily, number>;\n /** One-per-scope token.accounted cost snapshot. Updated when a later\n * token.accounted event has a later timestamp for the same scope. */\n}\n\n/**\n * Exported for the SQLite query engine (`sqlite-query.ts`).\n *\n * Filtering and summarisation are the parts of `ChronicleQuery` with real\n * semantics \u2014 family classification, nested `usage.*` attribute paths, cost\n * de-duplication by scope, a p95 over every matching duration. Re-expressing\n * those in SQL would create a second definition that drifts from this one, and\n * the drift would show up as quietly different numbers rather than an error.\n * The SQLite engine therefore uses SQL only to narrow candidates, then runs\n * these exact functions over the parsed events.\n */\nexport function createSummaryAccumulator(): SummaryAcc {\n return {\n logicalRequestIds: new Set(), modelAttempts: 0, completedAttempts: 0, failedAttempts: 0,\n scheduledRetries: 0, fallbacks: 0, providers: new Set(), models: new Set(),\n inputTokens: 0, outputTokens: 0, cacheReadTokens: 0, cacheWriteTokens: 0,\n costByScope: new Map(), providerDurations: [],\n toolCalls: 0, completedTools: 0, failedTools: 0, toolDurations: [],\n processes: 0, failedProcesses: 0,\n fileEvents: 0, uniqueFiles: new Set(), agentEvents: 0, uniqueAgents: new Set(),\n decisions: 0, escalations: 0, failures: 0, cancellations: 0,\n families: { llm: 0, agent: 0, tool: 0, file: 0, memory: 0, task: 0, decision: 0, runtime: 0, finding: 0 },\n failuresByFamily: { llm: 0, agent: 0, tool: 0, file: 0, memory: 0, task: 0, decision: 0, runtime: 0, finding: 0 },\n };\n}\n\nexport function updateSummary(acc: SummaryAcc, event: ChronicleEvent): void {\n // Families\n const family = signalFamily(event);\n acc.families[family]++;\n if (isTerminalFailure(event)) acc.failuresByFamily[family]++;\n\n // Running counts per event type\n if (event.correlation.logicalRequestId) acc.logicalRequestIds.add(event.correlation.logicalRequestId);\n if (event.runtime?.providerId) acc.providers.add(event.runtime.providerId);\n if (event.runtime?.modelId) acc.models.add(event.runtime.modelId);\n\n if (event.eventType === 'provider.attempt.started') acc.modelAttempts++;\n else if (event.eventType === 'provider.attempt.completed') {\n acc.completedAttempts++;\n acc.inputTokens += numberAt(event, 'usage.input');\n acc.outputTokens += numberAt(event, 'usage.output');\n acc.cacheReadTokens += numberAt(event, 'usage.cacheRead');\n acc.cacheWriteTokens += numberAt(event, 'usage.cacheWrite');\n const dur = durationMs(event);\n if (dur > 0) acc.providerDurations.push(dur);\n } else if (event.eventType === 'provider.attempt.failed') {\n acc.failedAttempts++;\n if (event.attributes?.retryScheduled === true) acc.scheduledRetries++;\n const dur = durationMs(event);\n if (dur > 0) acc.providerDurations.push(dur);\n } else if (event.eventType === 'provider.fallback') acc.fallbacks++;\n else if (event.eventType === 'tool.started') acc.toolCalls++;\n else if (event.eventType === 'tool.executed') {\n acc.completedTools++;\n const dur = durationMs(event);\n if (dur > 0) acc.toolDurations.push(dur);\n } else if (event.eventType === 'tool.failed') {\n acc.failedTools++;\n const dur = durationMs(event);\n if (dur > 0) acc.toolDurations.push(dur);\n } else if (event.eventType === 'process.started') acc.processes++;\n else if (event.eventType === 'process.completed' && event.outcome === 'failure') acc.failedProcesses++;\n else if (event.eventType === 'decision.requested') acc.decisions++;\n else if (event.eventType === 'decision.escalated') acc.escalations++;\n\n // Token accounted \u2014 keep the latest finite snapshot per scope. Zero is a\n // meaningful reset, and compareEvents makes ties independent of scan order.\n if (event.eventType === 'token.accounted') {\n const cost = readPath(event.attributes ?? {}, 'cost.total');\n if (typeof cost === 'number' && Number.isFinite(cost)) {\n const key = scopeKey(event);\n const existing = acc.costByScope.get(key);\n if (!existing || compareEvents(event, existing.event) > 0) {\n acc.costByScope.set(key, { cost, event });\n }\n }\n }\n\n // File evidence\n if (event.resource?.kind === 'file' || event.eventType.startsWith('file.')) {\n acc.fileEvents++;\n if (event.resource?.path) acc.uniqueFiles.add(event.resource.path);\n }\n\n // Agent events\n if (family === 'agent') acc.agentEvents++;\n if (event.scope.agentId) acc.uniqueAgents.add(event.scope.agentId);\n\n // Terminal failures and cancellations\n if (isTerminalFailure(event)) acc.failures++;\n if (event.outcome === 'cancelled' || event.outcome === 'abandoned') acc.cancellations++;\n}\n\nexport function finalizeSummary(acc: SummaryAcc): ChronicleSummary {\n const sortedProviderDurations = acc.providerDurations.slice().sort((a, b) => a - b);\n const sortedToolDurations = acc.toolDurations.slice().sort((a, b) => a - b);\n const totalCost = [...acc.costByScope.values()].reduce((sum, entry) => sum + entry.cost, 0);\n return {\n logicalRequests: acc.logicalRequestIds.size,\n modelAttempts: acc.modelAttempts,\n completedAttempts: acc.completedAttempts,\n failedAttempts: acc.failedAttempts,\n scheduledRetries: acc.scheduledRetries,\n fallbacks: acc.fallbacks,\n providers: acc.providers.size,\n models: acc.models.size,\n inputTokens: acc.inputTokens,\n outputTokens: acc.outputTokens,\n cacheReadTokens: acc.cacheReadTokens,\n cacheWriteTokens: acc.cacheWriteTokens,\n estimatedCostUsd: totalCost,\n providerAvgDurationMs: average(sortedProviderDurations),\n providerP95DurationMs: percentile(sortedProviderDurations, 0.95),\n toolCalls: acc.toolCalls,\n completedTools: acc.completedTools,\n failedTools: acc.failedTools,\n toolAvgDurationMs: average(sortedToolDurations),\n processes: acc.processes,\n failedProcesses: acc.failedProcesses,\n fileEvents: acc.fileEvents,\n uniqueFiles: acc.uniqueFiles.size,\n agentEvents: acc.agentEvents,\n uniqueAgents: acc.uniqueAgents.size,\n decisions: acc.decisions,\n escalations: acc.escalations,\n failures: acc.failures,\n cancellations: acc.cancellations,\n families: acc.families,\n failuresByFamily: acc.failuresByFamily,\n };\n}\n\n// \u2500\u2500 Partition discovery (no pre-loading) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n/** The partition files list is stored on the prototype for legacy callers\n * that reference engine.partitionFiles directly. */\nObject.defineProperty(ChronicleQueryEngine.prototype, 'partitionFiles', {\n get() { throw new Error('ChronicleQueryEngine no longer loads events on construction. Use async query().'); },\n set(this: ChronicleQueryEngine, _val: string[]) {\n // Allow fromFiles/fromDirectory to attach the list for graph()\n Object.defineProperty(this, 'partitionFiles', { value: _val, writable: false, configurable: false });\n },\n});\n\n/** Recursively locate journal partition files under a Chronicle directory,\n * ordered family-first then rotation index. Shared with the metrics store. */\nexport async function findChroniclePartitions(root: string): Promise<string[]> {\n return findPartitions(root);\n}\n\nasync function findPartitions(root: string): Promise<string[]> {\n const result: string[] = [];\n const visit = async (directory: string): Promise<void> => {\n let entries: import('node:fs').Dirent[];\n try { entries = await fs.readdir(directory, { withFileTypes: true }); } catch { return; }\n for (const entry of entries) {\n const full = path.join(directory, entry.name);\n if (entry.isDirectory()) await visit(full);\n else if (entry.isFile() && PARTITION_FILE_PATTERN.test(entry.name)) result.push(full);\n }\n };\n await visit(root);\n return result.sort(comparePartitionPaths);\n}\n\n// \u2500\u2500 Helper functions \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nfunction numberAt(event: ChronicleEvent, dotPath: string): number {\n const value = readPath(event.attributes ?? {}, dotPath);\n return typeof value === 'number' && Number.isFinite(value) ? value : 0;\n}\n\nfunction durationMs(event: ChronicleEvent): number {\n const value = Number(event.durationNs ?? 0) / 1_000_000;\n return Number.isFinite(value) ? value : 0;\n}\n\nfunction average(values: number[]): number {\n return values.length ? values.reduce((sum, v) => sum + v, 0) / values.length : 0;\n}\n\nfunction percentile(sorted: number[], quantile: number): number {\n return sorted.length ? sorted[Math.min(sorted.length - 1, Math.max(0, Math.ceil(sorted.length * quantile) - 1))]! : 0;\n}\n\nfunction scopeKey(event: ChronicleEvent): string {\n return `${event.scope.projectId ?? ''}\\0${event.scope.sessionId ?? ''}\\0${event.scope.agentId ?? ''}`;\n}\n\n/** Shared with ChronicleMetricsStore so its default-view summary classifies\n * events identically to the raw-scan summary it stands in for. */\nexport function signalFamily(event: ChronicleEvent): ChronicleSignalFamily {\n if (/^(?:decision|brain|permission)\\./.test(event.eventType)) return 'decision';\n if (event.resource?.kind === 'file' || event.resource?.kind === 'symbol' || /^(?:file|worktree)\\./.test(event.eventType)) return 'file';\n if (/^(?:provider|token|context|ctx|compaction)\\./.test(event.eventType)) return 'llm';\n if (/^(?:agent|subagent|delegate|fleet|concurrency)\\./.test(event.eventType)) return 'agent';\n if (/^(?:tool|process|mcp|network)\\./.test(event.eventType)) return 'tool';\n if (/^(?:memory|storage|trust)\\./.test(event.eventType)) return 'memory';\n if (/^(?:sdd|task|kanban|checkpoint|session|iteration|in_flight)\\./.test(event.eventType)) return 'task';\n if (/^(?:finding|review)\\./.test(event.eventType)) return 'finding';\n return 'runtime';\n}\n\n/** Shared with ChronicleMetricsStore \u2014 see signalFamily(). */\nexport function isTerminalFailure(event: ChronicleEvent): boolean {\n if (event.eventType === 'provider.attempt.failed') return event.attributes?.retryScheduled !== true;\n return event.eventType === 'tool.failed' ||\n (event.eventType === 'process.completed' && event.outcome === 'failure') ||\n /^(?:agent\\.run\\.error|sdd\\.task\\.failed|compaction\\.failed|network\\.request\\.failed)$/.test(event.eventType);\n}\n\n/**\n * Exported for the SQLite engine. Which correlation keys an event carries \u2014 and\n * with what confidence \u2014 is the definition of a Chronicle edge; a second copy\n * would let the two engines draw different graphs from the same data.\n */\nexport function relationKeys(event: ChronicleEvent): Array<{ key: string; kind: ChronicleRelationKind; confidence: ChronicleGraphEdge['confidence'] }> {\n const result: Array<{ key: string; kind: ChronicleRelationKind; confidence: ChronicleGraphEdge['confidence'] }> = [];\n const add = (kind: ChronicleRelationKind, value: unknown, confidence: ChronicleGraphEdge['confidence']) => {\n if (typeof value === 'string' && value) result.push({ key: `${kind}:${value}`, kind, confidence });\n };\n add('trace', event.correlation.traceId, 'correlated');\n add('tool_call', event.correlation.toolCallId, 'explicit');\n add('logical_request', event.correlation.logicalRequestId, 'explicit');\n add('attempt', event.correlation.attemptId, 'explicit');\n add('decision', event.attributes?.decisionId, 'explicit');\n add('network_request', event.attributes?.requestId, 'explicit');\n add('prompt_manifest', (event.attributes?.promptManifest as Record<string, unknown> | undefined)?.manifestId, 'explicit');\n add('resource_lineage', event.resource?.id, 'inferred');\n // tool.resource.observed is windowed into one metrics.rollup event per\n // tool call (rollup-adapter.ts) carrying a bounded `resources` list rather\n // than a single top-level `resource` \u2014 surface each as its own edge so a\n // rolled-up \"observed\" touch still participates in the same resource\n // lineage group as a mutation event for the same resource id.\n if (event.eventType === 'metrics.rollup' && event.attributes?.signal === 'tool.resource.observed') {\n const resources = event.attributes.resources as Array<{ id?: unknown }> | undefined;\n for (const resource of resources ?? []) {\n if (typeof resource?.id === 'string') add('resource_lineage', resource.id, 'inferred');\n }\n }\n if (event.correlation.parentSpanId) add('parent_span', event.correlation.parentSpanId, 'explicit');\n add('parent_span', event.correlation.spanId, 'explicit');\n return result;\n}\n\nexport function matches(event: ChronicleEvent, query: ChronicleQuery): boolean {\n if (query.eventId && event.eventId !== query.eventId) return false;\n if (query.eventTypes && !query.eventTypes.includes(event.eventType)) return false;\n if (query.outcomes && (!event.outcome || !query.outcomes.includes(event.outcome))) return false;\n const occurredAt = event.occurredAt ?? event.observedAt;\n if (query.from && occurredAt < query.from || query.to && occurredAt > query.to) return false;\n if (!equal(query.projectId, event.scope.projectId) || !equal(query.sessionId, event.scope.sessionId)) return false;\n if (!equal(query.agentId, event.scope.agentId) || !equal(query.taskId, event.scope.taskId)) return false;\n if (!equal(query.providerId, event.runtime?.providerId) || !equal(query.modelId, event.runtime?.modelId)) return false;\n if (!equal(query.traceId, event.correlation.traceId) || !equal(query.logicalRequestId, event.correlation.logicalRequestId)) return false;\n if (!equal(query.attemptId, event.correlation.attemptId) || !equal(query.toolCallId, event.correlation.toolCallId)) return false;\n if (!equal(query.resourceKind, event.resource?.kind) || !equal(query.resourceId, event.resource?.id)) return false;\n if (query.path && normalize(event.resource?.path) !== normalize(query.path)) return false;\n if (query.line !== undefined && !lineContains(event, query.line)) return false;\n if (query.tags && !objectContains(event.tags, query.tags)) return false;\n if (query.attributes && !objectContains(event.attributes, query.attributes)) return false;\n if (query.text && !JSON.stringify(event).toLocaleLowerCase().includes(query.text.toLocaleLowerCase())) return false;\n return true;\n}\n\nfunction equal<T>(expected: T | undefined, actual: T | undefined): boolean { return expected === undefined || expected === actual; }\nfunction normalize(value: string | undefined): string | undefined { return value?.replaceAll('\\\\', '/').toLocaleLowerCase(); }\nfunction lineContains(event: ChronicleEvent, line: number): boolean {\n const start = event.resource?.lineStart; const end = event.resource?.lineEnd ?? start;\n return start !== undefined && end !== undefined && line >= start && line <= end;\n}\nfunction objectContains(actual: Record<string, unknown> | undefined, expected: Record<string, unknown>): boolean {\n return Boolean(actual && Object.entries(expected).every(([key, value]) => deepEqual(readPath(actual, key), value)));\n}\nfunction readPath(value: Record<string, unknown>, key: string): unknown {\n return key.split('.').reduce<unknown>((current, part) => current && typeof current === 'object'\n ? (current as Record<string, unknown>)[part] : undefined, value);\n}\nfunction deepEqual(left: unknown, right: unknown): boolean { return JSON.stringify(left) === JSON.stringify(right); }\nfunction findInsertionIndex(\n events: readonly ChronicleEvent[],\n event: ChronicleEvent,\n compare: (left: ChronicleEvent, right: ChronicleEvent) => number,\n): number {\n let low = 0;\n let high = events.length;\n while (low < high) {\n const middle = (low + high) >>> 1;\n if (compare(events[middle]!, event) <= 0) low = middle + 1;\n else high = middle;\n }\n return low;\n}\nexport function compareEvents(a: ChronicleEvent, b: ChronicleEvent): number {\n return compareEventToKey(a, orderKey(b));\n}\nfunction compareEventToKey(event: ChronicleEvent, key: ChronicleOrderKey): number {\n return (event.occurredAt ?? event.observedAt).localeCompare(key.occurredAt) ||\n event.persistedAt.localeCompare(key.persistedAt) || event.sequence - key.sequence ||\n event.eventId.localeCompare(key.eventId);\n}\nfunction orderKey(event: ChronicleEvent): ChronicleOrderKey {\n return {\n occurredAt: event.occurredAt ?? event.observedAt,\n persistedAt: event.persistedAt,\n sequence: event.sequence,\n eventId: event.eventId,\n };\n}\nfunction hashQuery(query: ChronicleQuery): string {\n const { cursor: _cursor, limit: _limit, order: _order, ...filters } = query;\n return createHash('sha256').update(stableStringify(filters), 'utf8').digest('base64url');\n}\nfunction encodeCursor(cursor: ChronicleCursor): string {\n return Buffer.from(JSON.stringify(cursor), 'utf8').toString('base64url');\n}\nfunction decodeCursor(\n encoded: string | undefined,\n order: 'asc' | 'desc',\n queryHash: string,\n): ChronicleCursor | undefined {\n if (!encoded) return undefined;\n if (encoded.length > 1_000_000) throw new Error('Invalid Chronicle cursor');\n try {\n const parsed = JSON.parse(Buffer.from(encoded, 'base64url').toString('utf8')) as unknown;\n if (!isCursor(parsed) || parsed.order !== order || parsed.queryHash !== queryHash) {\n throw new Error('cursor does not match the query');\n }\n return parsed;\n } catch (error) {\n throw new Error(`Invalid Chronicle cursor: ${error instanceof Error ? error.message : String(error)}`);\n }\n}\nfunction isCursor(value: unknown): value is ChronicleCursor {\n if (!value || typeof value !== 'object') return false;\n const cursor = value as Partial<ChronicleCursor>;\n const after = cursor.after as Partial<ChronicleOrderKey> | undefined;\n if (cursor.version !== 1 || (cursor.order !== 'asc' && cursor.order !== 'desc') ||\n typeof cursor.queryHash !== 'string' || !after ||\n typeof after.occurredAt !== 'string' || typeof after.persistedAt !== 'string' ||\n !Number.isSafeInteger(after.sequence) || typeof after.eventId !== 'string' ||\n !Array.isArray(cursor.snapshot) || cursor.snapshot.length > MAX_CURSOR_SNAPSHOT_ENTRIES) return false;\n\n const snapshotIds = new Set<string>();\n for (const entry of cursor.snapshot) {\n if (!entry || typeof entry.id !== 'string' || !entry.id ||\n !Number.isSafeInteger(entry.size) || entry.size < 0 || snapshotIds.has(entry.id)) return false;\n snapshotIds.add(entry.id);\n }\n return true;\n}\nasync function captureSnapshot(files: readonly string[]): Promise<SnapshotFile[]> {\n if (files.length > MAX_CURSOR_SNAPSHOT_ENTRIES) {\n throw new Error('Chronicle snapshot contains too many partitions');\n }\n return Promise.all(files.map(async (file) => {\n let size = 0;\n try { size = (await fs.stat(file)).size; } catch { /* preserve missing source as empty */ }\n return { file, id: fileId(file), size };\n }));\n}\nasync function resolveSnapshotFiles(\n files: readonly string[],\n snapshot: readonly ChronicleSnapshotEntry[],\n): Promise<SnapshotFile[]> {\n const currentFiles = new Map(files.map((file) => [fileId(file), file]));\n return Promise.all(snapshot.map(async (entry) => {\n const file = currentFiles.get(entry.id);\n if (!file) throw new Error('Chronicle cursor snapshot has expired');\n let currentSize: number;\n try { currentSize = (await fs.stat(file)).size; } catch { throw new Error('Chronicle cursor snapshot has expired'); }\n if (currentSize < entry.size) throw new Error('Chronicle cursor snapshot has expired');\n return { file, ...entry };\n }));\n}\nfunction fileId(file: string): string {\n return createHash('sha256').update(path.resolve(file), 'utf8').digest('base64url');\n}\nfunction stableStringify(value: unknown): string {\n if (value === null || typeof value !== 'object') return JSON.stringify(value);\n if (Array.isArray(value)) return `[${value.map(stableStringify).join(',')}]`;\n const object = value as Record<string, unknown>;\n return `{${Object.keys(object).sort().map((key) => `${JSON.stringify(key)}:${stableStringify(object[key])}`).join(',')}}`;\n}\nfunction isChronicleEvent(value: unknown): value is ChronicleEvent {\n if (!isRecord(value) || !isRecord(value.scope) || !isRecord(value.correlation)) return false;\n return value.schemaVersion === 1 &&\n typeof value.eventId === 'string' && typeof value.eventType === 'string' &&\n typeof value.occurredAt === 'string' && typeof value.observedAt === 'string' &&\n typeof value.persistedAt === 'string' && Number.isSafeInteger(value.sequence) &&\n (value.sequence as number) >= 0 && typeof value.previousHash === 'string' &&\n typeof value.hash === 'string' && typeof value.scope.installationId === 'string' &&\n typeof value.scope.machineId === 'string' && optionalStrings(value.scope, [\n 'projectId', 'repositoryId', 'workspaceId', 'worktreeId', 'sessionId', 'turnId',\n 'iterationId', 'agentId', 'goalId', 'planId', 'taskId', 'kanbanBoardId',\n ]) && typeof value.correlation.traceId === 'string' &&\n typeof value.correlation.spanId === 'string' && optionalStrings(value.correlation, [\n 'parentSpanId', 'logicalRequestId', 'attemptId', 'toolCallId',\n ]) && isRuntime(value.runtime) && isResource(value.resource) &&\n (value.attributes === undefined || isRecord(value.attributes)) &&\n (value.tags === undefined || isStringRecord(value.tags));\n}\nfunction isRuntime(value: unknown): boolean {\n return value === undefined || isRecord(value) &&\n optionalStrings(value, ['providerId', 'modelId', 'modelRevision']) &&\n optionalFiniteNumbers(value, ['processId', 'parentProcessId']);\n}\nfunction isResource(value: unknown): boolean {\n if (value === undefined) return true;\n if (!isRecord(value) || !['file', 'symbol', 'memory', 'task', 'kanban', 'process',\n 'network', 'artifact', 'other'].includes(String(value.kind)) || typeof value.id !== 'string') return false;\n return optionalStrings(value, ['path', 'contentHashBefore', 'contentHashAfter']) &&\n optionalFiniteNumbers(value, ['lineStart', 'lineEnd']);\n}\nfunction optionalStrings(value: Record<string, unknown>, keys: readonly string[]): boolean {\n return keys.every((key) => value[key] === undefined || typeof value[key] === 'string');\n}\nfunction optionalFiniteNumbers(value: Record<string, unknown>, keys: readonly string[]): boolean {\n return keys.every((key) => value[key] === undefined || typeof value[key] === 'number' && Number.isFinite(value[key]));\n}\nfunction isStringRecord(value: unknown): value is Record<string, string> {\n return isRecord(value) && Object.values(value).every((entry) => typeof entry === 'string');\n}\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return Boolean(value && typeof value === 'object' && !Array.isArray(value));\n}\nexport function facetValue(event: ChronicleEvent, field: ChronicleFacet): string | undefined {\n const values: Record<ChronicleFacet, string | undefined> = {\n eventType: event.eventType, outcome: event.outcome, projectId: event.scope.projectId,\n sessionId: event.scope.sessionId, agentId: event.scope.agentId, taskId: event.scope.taskId,\n providerId: event.runtime?.providerId, modelId: event.runtime?.modelId,\n resourceKind: event.resource?.kind, resourcePath: event.resource?.path,\n toolCallId: event.correlation.toolCallId,\n };\n return values[field];\n}\n", "import * as fs from 'node:fs/promises';\nimport * as path from 'node:path';\nimport { atomicWrite, withFileLock } from '../utils/atomic-write.js';\n\nconst CACHE_VERSION = 1;\n\nexport interface ChroniclePartitionRange {\n size: number;\n minOccurredAt?: string;\n maxOccurredAt?: string;\n /** No valid events were found in the file. */\n empty?: boolean;\n}\n\ninterface CacheFile {\n version: number;\n entries: Record<string, ChroniclePartitionRange>;\n}\n\nfunction isRange(value: unknown): value is ChroniclePartitionRange {\n if (!value || typeof value !== 'object') return false;\n const range = value as Partial<ChroniclePartitionRange>;\n return (\n typeof range.size === 'number' &&\n (range.minOccurredAt === undefined || typeof range.minOccurredAt === 'string') &&\n (range.maxOccurredAt === undefined || typeof range.maxOccurredAt === 'string') &&\n (range.empty === undefined || typeof range.empty === 'boolean')\n );\n}\n\n/**\n * Persisted cache of each closed (immutable) Chronicle partition file's\n * observed min/max `occurredAt`, so query()/facets() can skip a file\n * entirely instead of re-streaming its contents when it can't overlap a\n * time-bounded query. Keyed by (path, size) so a file whose size ever\n * unexpectedly changes just misses and gets recomputed.\n */\nexport class ChroniclePartitionRangeCache {\n private readonly cachePath: string;\n private entries: Map<string, ChroniclePartitionRange> | undefined;\n private dirty = false;\n\n constructor(private readonly directory: string) {\n this.cachePath = path.join(directory, 'range-cache.json');\n }\n\n private toKey(filePath: string): string {\n return path.relative(this.directory, filePath).split(path.sep).join('/');\n }\n\n private async load(): Promise<Map<string, ChroniclePartitionRange>> {\n if (this.entries) return this.entries;\n const entries = new Map<string, ChroniclePartitionRange>();\n try {\n const raw = await fs.readFile(this.cachePath, 'utf8');\n const parsed = JSON.parse(raw) as Partial<CacheFile>;\n if (parsed.version === CACHE_VERSION && parsed.entries && typeof parsed.entries === 'object') {\n for (const [key, range] of Object.entries(parsed.entries)) {\n if (isRange(range)) entries.set(key, range);\n }\n }\n } catch {\n // Missing, corrupt, or unreadable sidecar: self-heal by starting\n // empty rather than failing the query it's meant to speed up.\n }\n this.entries = entries;\n return entries;\n }\n\n async get(filePath: string, currentSize: number): Promise<ChroniclePartitionRange | undefined> {\n const entries = await this.load();\n const range = entries.get(this.toKey(filePath));\n return range && range.size === currentSize ? range : undefined;\n }\n\n set(filePath: string, range: ChroniclePartitionRange): void {\n this.entries ??= new Map();\n this.entries.set(this.toKey(filePath), range);\n this.dirty = true;\n }\n\n /** Drop entries for files no longer present (e.g. removed by retention purge). */\n prune(existingFiles: readonly string[]): void {\n if (!this.entries) return;\n const keep = new Set(existingFiles.map((file) => this.toKey(file)));\n for (const key of this.entries.keys()) {\n if (!keep.has(key)) {\n this.entries.delete(key);\n this.dirty = true;\n }\n }\n }\n\n async flush(): Promise<void> {\n if (!this.dirty || !this.entries) return;\n const payload: CacheFile = { version: CACHE_VERSION, entries: Object.fromEntries(this.entries) };\n try {\n await withFileLock(this.cachePath, async () => {\n await atomicWrite(this.cachePath, `${JSON.stringify(payload)}\\n`, { mode: 0o600 });\n });\n this.dirty = false;\n } catch {\n // Best-effort persistence: the cache still works in-memory for this\n // process even if the sidecar couldn't be written this time.\n }\n }\n}\n", "/**\n * One-shot import of the legacy JSONL journal into SQLite\n * (phase 2 of `chronicle-sqlite-journal-v1`).\n *\n * The events being moved are an audit record, so this is deliberately strict:\n * every event is verified against the running chain *before* it is inserted,\n * and a single break aborts that day inside a rolled-back transaction.\n * Repairing a broken chain silently would defeat the purpose of having one \u2014\n * the operator is told exactly where it broke and decides.\n *\n * Chains are scoped to a day family (`<day>.events.jsonl` plus its `.NNNNN`\n * rotations), not to the journal as a whole: `sequence` restarts at 1 each day.\n * Each family is therefore imported as its own chain and its own transaction,\n * seeded from that family's `*.retention.json` checkpoint when its prefix was\n * already purged.\n *\n * A family that fails verification is quarantined \u2014 never imported, never\n * repaired, recorded by day so health can report it \u2014 and the remaining days\n * still move. Scoping the abort to the journal instead made every future day\n * hostage to the worst day on disk: one multi-writer partition from before the\n * single-daemon invariant, and the store could never finish opening, so\n * Chronicle recorded nothing at all from then on.\n */\nimport * as fs from 'node:fs/promises';\nimport * as path from 'node:path';\nimport { chronicleEventHash, GENESIS_HASH } from './event-hash.js';\nimport { collectPartitions, readRetentionCheckpoint, streamEntriesStrict } from './journal.js';\nimport { PARTITION_FILE_PATTERN } from './partition-filename.js';\nimport type {\n ChronicleQuarantinedFamily,\n ChronicleSqliteJournal,\n} from './sqlite-journal.js';\n\nexport interface ChronicleLegacyImportResult {\n /** True when the marker was already set and nothing was read. */\n alreadyImported: boolean;\n /** Day families imported. */\n families: number;\n /** Events imported across all families. */\n events: number;\n /** Day families refused for a broken chain; none of their events landed. */\n quarantined: ChronicleQuarantinedFamily[];\n}\n\n/** A chain break found while importing; carries enough context to act on. */\nexport class ChronicleImportError extends Error {\n constructor(\n message: string,\n readonly day: string,\n readonly sequence: number,\n ) {\n super(message);\n this.name = 'ChronicleImportError';\n }\n}\n\n/**\n * Discover the day families in a chronicle directory.\n *\n * `PARTITION_FILE_PATTERN` captures the family base (`<day>.events`) separately\n * from the rotation index, so rotations collapse onto the family they belong\n * to instead of being mistaken for separate days.\n */\nasync function discoverFamilies(directory: string): Promise<string[]> {\n let entries: string[];\n try {\n entries = await fs.readdir(directory);\n } catch {\n return [];\n }\n const bases = new Set<string>();\n for (const entry of entries) {\n const match = PARTITION_FILE_PATTERN.exec(entry);\n if (match?.[1]) bases.add(match[1]);\n }\n return [...bases].sort();\n}\n\n/** `2026-07-28.events` \u2192 `2026-07-28`. */\nfunction dayOfFamily(familyBase: string): string {\n return familyBase.replace(/\\.events$/u, '');\n}\n\nexport async function importLegacyChronicleJournal(\n journal: ChronicleSqliteJournal,\n directory: string,\n): Promise<ChronicleLegacyImportResult> {\n if (journal.hasImportedLegacyJournal()) {\n return {\n alreadyImported: true,\n families: 0,\n events: 0,\n quarantined: journal.quarantinedFamilies(),\n };\n }\n\n const families = await discoverFamilies(directory);\n const quarantined: ChronicleQuarantinedFamily[] = [];\n let importedEvents = 0;\n let importedFamilies = 0;\n\n for (const familyBase of families) {\n const day = dayOfFamily(familyBase);\n const basePath = path.join(directory, `${familyBase}.jsonl`);\n let familyEvents = 0;\n\n // Resume rather than restart. Families commit one at a time, so a run cut\n // short \u2014 the daemon restarted, the machine rebooted \u2014 leaves whole days\n // already stored. Re-reading them would abort on the `(day, sequence)`\n // primary key and put the import back to square one every time.\n if (journal.hasImportedDay(day)) continue;\n\n try {\n // One transaction per family: a break below rolls back this day only,\n // leaving the days already committed \u2014 and every future day \u2014 intact.\n await journal.runFamilyImport(async (sink) => {\n familyEvents = 0;\n\n const checkpointResult = await readRetentionCheckpoint(basePath);\n if (checkpointResult.error) {\n throw new ChronicleImportError(checkpointResult.error, day, 0);\n }\n const checkpoint = checkpointResult.checkpoint;\n if (checkpoint) sink.checkpoint(day, checkpoint.sequence, checkpoint.hash);\n\n let expectedSequence = (checkpoint?.sequence ?? 0) + 1;\n let previousHash = checkpoint?.hash ?? GENESIS_HASH;\n\n for (const partition of await collectPartitions(basePath)) {\n for await (const event of streamEntriesStrict(partition)) {\n if (event.sequence !== expectedSequence) {\n throw new ChronicleImportError(\n `sequence gap in ${day}: expected ${expectedSequence}, found ${event.sequence}`,\n day,\n event.sequence,\n );\n }\n if (event.previousHash !== previousHash) {\n throw new ChronicleImportError(\n `previous hash mismatch in ${day} at sequence ${event.sequence}`,\n day,\n event.sequence,\n );\n }\n if (chronicleEventHash(event) !== event.hash) {\n throw new ChronicleImportError(\n `entry hash mismatch in ${day} at sequence ${event.sequence}`,\n day,\n event.sequence,\n );\n }\n sink.insert(day, event);\n familyEvents += 1;\n expectedSequence = event.sequence + 1;\n previousHash = event.hash;\n }\n }\n });\n } catch (error) {\n // A broken chain is data the operator has to decide about, so it is\n // quarantined and reported. Anything else \u2014 an unreadable file, a full\n // disk, SQLite refusing to write \u2014 is an infrastructure failure that\n // would corrupt the import if treated as \"just skip that day\".\n if (!(error instanceof ChronicleImportError)) throw error;\n quarantined.push({ day, sequence: error.sequence, reason: error.message });\n continue;\n }\n\n if (familyEvents > 0) importedFamilies += 1;\n importedEvents += familyEvents;\n }\n\n journal.recordQuarantinedFamilies(quarantined);\n journal.markLegacyJournalImported();\n\n return {\n alreadyImported: false,\n families: importedFamilies,\n events: importedEvents,\n quarantined,\n };\n}\n", "/**\n * SQLite-backed Chronicle journal (phase 1 of `chronicle-sqlite-journal-v1`).\n *\n * Same durable contract as `ChronicleJournal`, different storage: events become\n * rows instead of lines in `<day>.events.jsonl` partitions. The tamper-evident\n * chain is unchanged and deliberately so \u2014 `sequence`, `previousHash` and\n * `hash` mean exactly what they mean in the JSONL journal, and the hash is\n * computed by the shared `event-hash.ts` so the two stores can never drift.\n *\n * Why the payload is stored verbatim: the `hash` preimage is the canonical\n * encoding of the event *minus* its own `hash`. Reconstructing an event from\n * projected columns and re-hashing it would silently depend on the column set\n * staying lossless forever. Storing `JSON.stringify(event)` and re-deriving the\n * preimage from the parsed payload keeps verification independent of the\n * projection \u2014 the columns are a read-path index, never the source of truth.\n *\n * Only the project daemon opens this database, after it has won the endpoint\n * election, so the writer is single by construction and `BEGIN IMMEDIATE` is\n * enough. See `packages/core/tests/architecture/project-daemon-boundary.test.ts`.\n */\nimport { randomUUID } from 'node:crypto';\nimport { createRequire } from 'node:module';\nimport * as path from 'node:path';\nimport type { DatabaseSync } from 'node:sqlite';\nimport { withSqliteExperimentalWarningSuppressed } from '../utils/index.js';\nimport { chronicleEventHash, GENESIS_HASH, hashValue } from './event-hash.js';\nimport type { ChronicleJournalStats, ChroniclePurgeResult } from './journal.js';\nimport {\n ChronicleSqliteQueryEngine,\n type ChronicleSqliteQueryEngineOptions,\n} from './sqlite-query.js';\nimport {\n CHRONICLE_SCHEMA_VERSION,\n type ChronicleEvent,\n type ChronicleEventInput,\n type ChronicleVerifyResult,\n} from './types.js';\n\nexport const CHRONICLE_SQLITE_FILE = 'chronicle.sqlite';\n\n/** Marker written once the legacy JSONL partitions have been imported. */\nexport const LEGACY_JSONL_MIGRATION_KEY = 'legacy-jsonl-v1';\n\n/** Day families the import refused to move, recorded so they are never retried silently. */\nexport const LEGACY_JSONL_QUARANTINE_KEY = 'legacy-jsonl-v1:quarantine';\n\nconst SCHEMA_VERSION = 1;\n\nexport interface ChronicleSqliteJournalOptions {\n /** Directory holding the journal, i.e. `<projectDir>/chronicle`. */\n directory: string;\n now?: (() => Date) | undefined;\n monotonicNow?: (() => bigint) | undefined;\n idFactory?: (() => string) | undefined;\n}\n\nexport interface ChronicleSqlitePurgeOptions {\n retentionDays: number;\n dryRun?: boolean | undefined;\n}\n\ninterface ChainAnchor {\n sequence: number;\n hash: string;\n}\n\n/** A day family the import refused to move, and why. */\nexport interface ChronicleQuarantinedFamily {\n day: string;\n sequence: number;\n reason: string;\n}\n\n/** Write surface handed to a legacy import; see {@link ChronicleSqliteJournal.runFamilyImport}. */\nexport interface ChronicleImportSink {\n /**\n * Store an event with its recorded `sequence`, `previousHash` and `hash`.\n *\n * The payload is re-serialized rather than copied byte-for-byte from the\n * JSONL line, which is safe because the hash preimage is the *canonical*\n * encoding derived from the parsed event (\u00A73.1 of the spec) \u2014 not the stored\n * bytes. `JSON.parse` round-trips it exactly, so verification is unaffected.\n */\n insert(day: string, event: ChronicleEvent): void;\n /** Carry a legacy day-family retention checkpoint over. */\n checkpoint(day: string, sequence: number, hash: string): void;\n}\n\n// \u2500\u2500\u2500 node:sqlite lazy loader (mirrors metrics-store.ts) \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nlet Ctor: typeof DatabaseSync | null | undefined;\n\nfunction loadDatabaseSync(): typeof DatabaseSync {\n if (Ctor) return Ctor;\n if (Ctor === null) throw new Error('node:sqlite is unavailable in this runtime');\n try {\n Ctor = withSqliteExperimentalWarningSuppressed(\n () =>\n (createRequire(import.meta.url)('node:sqlite') as typeof import('node:sqlite')).DatabaseSync,\n );\n return Ctor;\n } catch (error) {\n Ctor = null;\n throw new Error(\n \"The Chronicle journal needs Node's built-in SQLite (node:sqlite, Node >= 22.5): \" +\n (error instanceof Error ? error.message : String(error)),\n );\n }\n}\n\n// \u2500\u2500\u2500 Store \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport class ChronicleSqliteJournal {\n private readonly db: DatabaseSync;\n private readonly dbPath: string;\n private readonly now: () => Date;\n private readonly monotonicNow: () => bigint;\n private readonly idFactory: () => string;\n\n /**\n * Cached chain head per day. Cleared wholesale on any write failure so the\n * next append rebuilds from the database rather than trusting a counter that\n * may have advanced past what actually committed.\n */\n private readonly anchors = new Map<string, ChainAnchor>();\n\n private readonly counters = {\n acceptedEvents: 0,\n persistedEvents: 0,\n rejectedEvents: 0,\n failedEvents: 0,\n batches: 0,\n maxObservedPending: 0,\n largestBatch: 0,\n };\n private lastBatchDurationMs: number | undefined;\n\n constructor(options: ChronicleSqliteJournalOptions) {\n this.dbPath = path.join(path.resolve(options.directory), CHRONICLE_SQLITE_FILE);\n this.now = options.now ?? (() => new Date());\n this.monotonicNow = options.monotonicNow ?? (() => process.hrtime.bigint());\n this.idFactory = options.idFactory ?? (() => randomUUID());\n const Database = loadDatabaseSync();\n this.db = new Database(this.dbPath);\n this.db.exec('PRAGMA journal_mode = WAL');\n this.ensureSchema();\n }\n\n close(): void {\n this.db.close();\n }\n\n stats(): ChronicleJournalStats {\n return {\n ...this.counters,\n pendingEvents: 0,\n // Retained at zero for wire compatibility: partitions do not exist here,\n // but `ChronicleJournalStats` is part of the IPC health payload.\n partitionRolls: 0,\n ...(this.lastBatchDurationMs !== undefined\n ? { lastBatchDurationMs: this.lastBatchDurationMs }\n : {}),\n };\n }\n\n /**\n * Writes are synchronous and transactional, so there is nothing buffered to\n * flush. Kept to satisfy `ChronicleEventSink`.\n */\n async flush(): Promise<void> {\n return Promise.resolve();\n }\n\n async append(input: ChronicleEventInput): Promise<ChronicleEvent> {\n const [event] = await this.appendBatch([input]);\n // appendBatch either returns one event per input or throws.\n return event as ChronicleEvent;\n }\n\n /**\n * Append a batch as one transaction.\n *\n * The chain is computed in memory from a single anchor, so a partially\n * applied batch would leave a hole in `sequence` that verification can never\n * reconcile. Rollback plus anchor invalidation is what prevents that.\n */\n async appendBatch(inputs: readonly ChronicleEventInput[]): Promise<ChronicleEvent[]> {\n if (inputs.length === 0) return [];\n const started = performance.now();\n this.counters.acceptedEvents += inputs.length;\n this.counters.batches += 1;\n this.counters.largestBatch = Math.max(this.counters.largestBatch, inputs.length);\n\n const instant = this.now().toISOString();\n // The chain scope is the wall-clock day of the append, matching the file\n // `journalForToday()` would have opened \u2014 not the event's `occurredAt`,\n // which a caller may back-date.\n const day = instant.slice(0, 10);\n const events: ChronicleEvent[] = [];\n let previous = this.readAnchor(day);\n\n for (const input of inputs) {\n const unhashed = {\n ...input,\n occurredAt: input.occurredAt ?? instant,\n monotonicNs: input.monotonicNs ?? this.monotonicNow().toString(),\n schemaVersion: CHRONICLE_SCHEMA_VERSION,\n eventId: this.idFactory(),\n observedAt: instant,\n persistedAt: instant,\n sequence: previous.sequence + 1,\n previousHash: previous.hash,\n };\n const event: ChronicleEvent = { ...unhashed, hash: hashValue(unhashed) };\n events.push(event);\n previous = { sequence: event.sequence, hash: event.hash };\n }\n\n try {\n this.db.exec('BEGIN IMMEDIATE');\n const insert = this.db.prepare(\n `INSERT INTO events (\n day, sequence, event_id, hash, previous_hash, occurred_at, event_type, outcome,\n project_id, session_id, agent_id, task_id, trace_id, logical_request_id,\n resource_kind, resource_id, resource_path, duration_ns, payload\n ) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,\n );\n for (const event of events) {\n const row = projectEvent(event);\n insert.run(\n day,\n event.sequence,\n event.eventId,\n event.hash,\n event.previousHash,\n row.occurredAt,\n event.eventType,\n row.outcome,\n row.projectId,\n row.sessionId,\n row.agentId,\n row.taskId,\n row.traceId,\n row.logicalRequestId,\n row.resourceKind,\n row.resourceId,\n row.resourcePath,\n row.durationNs,\n JSON.stringify(event),\n );\n }\n this.db.exec('COMMIT');\n } catch (error) {\n try {\n this.db.exec('ROLLBACK');\n } catch {\n // A failed BEGIN leaves no transaction to roll back.\n }\n this.anchors.clear();\n this.counters.failedEvents += inputs.length;\n this.lastBatchDurationMs = performance.now() - started;\n throw error;\n }\n\n this.anchors.set(day, previous);\n this.counters.persistedEvents += events.length;\n this.lastBatchDurationMs = performance.now() - started;\n return events;\n }\n\n async readAll(): Promise<ChronicleEvent[]> {\n const rows = this.db\n .prepare('SELECT payload FROM events ORDER BY day, sequence')\n .all() as Array<{ payload: string }>;\n return rows.map((row) => JSON.parse(row.payload) as ChronicleEvent);\n }\n\n /**\n * Walk every chain and prove none has been edited.\n *\n * Chronicle chains are scoped to a day, not to the journal: the JSONL writer\n * anchors each `<day>.events.jsonl` family at `GENESIS_HASH` independently,\n * so `sequence` restarts at 1 every day. Verification mirrors that \u2014 each day\n * is validated on its own, and a break in one does not implicate the others.\n *\n * Three independent properties per day, because each catches a different\n * failure: a dense `sequence` catches deletions from the middle, the\n * `previousHash` link catches reordering, and re-hashing the payload catches\n * an in-place edit that left the links intact.\n */\n async verify(): Promise<ChronicleVerifyResult> {\n let entries = 0;\n let lastSequence = 0;\n let lastHash = GENESIS_HASH;\n\n for (const day of this.days()) {\n const checkpoint = this.readCheckpoint(day);\n let expectedSequence = (checkpoint?.sequence ?? 0) + 1;\n let previousHash = checkpoint?.hash ?? GENESIS_HASH;\n\n const rows = this.db\n .prepare(\n 'SELECT sequence, hash, previous_hash, payload FROM events WHERE day = ? ORDER BY sequence',\n )\n .all(day) as Array<{\n sequence: number;\n hash: string;\n previous_hash: string;\n payload: string;\n }>;\n\n for (const row of rows) {\n if (row.sequence !== expectedSequence) {\n return {\n ok: false,\n entries,\n brokenAt: entries,\n reason: `sequence gap in ${day}: expected ${expectedSequence}, found ${row.sequence}`,\n };\n }\n if (row.previous_hash !== previousHash) {\n return { ok: false, entries, brokenAt: entries, reason: 'previous hash mismatch' };\n }\n let event: ChronicleEvent;\n try {\n event = JSON.parse(row.payload) as ChronicleEvent;\n } catch {\n return { ok: false, entries, brokenAt: entries, reason: 'invalid payload JSON' };\n }\n if (chronicleEventHash(event) !== row.hash) {\n return { ok: false, entries, brokenAt: entries, reason: 'entry hash mismatch' };\n }\n entries += 1;\n expectedSequence = row.sequence + 1;\n previousHash = row.hash;\n }\n\n lastSequence = expectedSequence - 1;\n lastHash = previousHash;\n }\n\n return { ok: true, entries, lastSequence, lastHash };\n }\n\n /**\n * Drop events older than the retention window.\n *\n * Retention is day-granular and chains are day-scoped, so a purge removes\n * whole chains rather than truncating one. That is why nothing needs to be\n * checkpointed here: there is no surviving suffix left dangling without an\n * anchor. Any checkpoint imported from a partially-purged legacy day family\n * is dropped alongside its events.\n */\n async purge(options: ChronicleSqlitePurgeOptions): Promise<ChroniclePurgeResult> {\n const empty: ChroniclePurgeResult = {\n deletedCount: 0,\n deletedBytes: 0,\n skippedCount: 0,\n errors: [],\n };\n if (!Number.isFinite(options.retentionDays) || options.retentionDays <= 0) return empty;\n\n const cutoff = new Date(this.now().getTime() - options.retentionDays * 86_400_000)\n .toISOString()\n .slice(0, 10);\n\n const count = (\n this.db.prepare('SELECT COUNT(*) AS n FROM events WHERE day < ?').get(cutoff) as {\n n: number;\n }\n ).n;\n if (count === 0) return empty;\n\n if (options.dryRun) {\n const days = this.db\n .prepare('SELECT DISTINCT day FROM events WHERE day < ? ORDER BY day')\n .all(cutoff) as Array<{ day: string }>;\n return { ...empty, deletedCount: count, candidates: days.map((row) => row.day) };\n }\n\n try {\n this.db.exec('BEGIN IMMEDIATE');\n this.db.prepare('DELETE FROM events WHERE day < ?').run(cutoff);\n this.db.prepare('DELETE FROM chain_checkpoint WHERE day < ?').run(cutoff);\n this.db.exec('COMMIT');\n } catch (error) {\n try {\n this.db.exec('ROLLBACK');\n } catch {\n // Nothing to unwind.\n }\n return {\n ...empty,\n errors: [\n {\n file: this.dbPath,\n reason: error instanceof Error ? error.message : String(error),\n },\n ],\n };\n }\n\n this.anchors.clear();\n return { ...empty, deletedCount: count };\n }\n\n /**\n * Run one day family's legacy import inside its own transaction.\n *\n * Deliberately separate from `appendBatch`: the append path *computes*\n * `sequence`, `previousHash` and `hash`, while an import must carry them over\n * untouched. Fusing the two would put a code path one refactor away from\n * re-hashing historical events, which is the one change that silently\n * destroys their tamper evidence.\n *\n * The transaction is scoped to a single family because chains are: `sequence`\n * restarts at 1 each day, so one day's break says nothing about the next\n * day's integrity. A whole-journal transaction made every future day hostage\n * to the worst day on disk \u2014 one corrupt family and the daemon could never\n * open its store again. The family is still all-or-nothing: a break rolls\n * back that day entirely, so no partial chain is ever visible.\n */\n async runFamilyImport(load: (sink: ChronicleImportSink) => Promise<void>): Promise<void> {\n const insert = this.db.prepare(\n `INSERT INTO events (\n day, sequence, event_id, hash, previous_hash, occurred_at, event_type, outcome,\n project_id, session_id, agent_id, task_id, trace_id, logical_request_id,\n resource_kind, resource_id, resource_path, duration_ns, payload\n ) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)`,\n );\n const checkpoint = this.db.prepare(\n `INSERT INTO chain_checkpoint (day, sequence, hash) VALUES (?, ?, ?)\n ON CONFLICT(day) DO UPDATE SET sequence = excluded.sequence, hash = excluded.hash`,\n );\n\n this.db.exec('BEGIN IMMEDIATE');\n try {\n await load({\n insert: (day, event) => {\n const row = projectEvent(event);\n insert.run(\n day,\n event.sequence,\n event.eventId,\n event.hash,\n event.previousHash,\n row.occurredAt,\n event.eventType,\n row.outcome,\n row.projectId,\n row.sessionId,\n row.agentId,\n row.taskId,\n row.traceId,\n row.logicalRequestId,\n row.resourceKind,\n row.resourceId,\n row.resourcePath,\n row.durationNs,\n JSON.stringify(event),\n );\n },\n checkpoint: (day, sequence, hash) => {\n checkpoint.run(day, sequence, hash);\n },\n });\n this.db.exec('COMMIT');\n } catch (error) {\n try {\n this.db.exec('ROLLBACK');\n } catch {\n // Nothing to unwind.\n }\n throw error;\n } finally {\n this.anchors.clear();\n }\n }\n\n /**\n * A read engine over this journal's own connection.\n *\n * Sharing the connection rather than opening a second one keeps the\n * single-writer guarantee intact and means a reader can never observe a\n * half-applied batch: SQLite serialises statements on one handle.\n */\n queryEngine(options?: ChronicleSqliteQueryEngineOptions): ChronicleSqliteQueryEngine {\n return new ChronicleSqliteQueryEngine(this.db, options);\n }\n\n /** Has the legacy JSONL import already run? */\n hasImportedLegacyJournal(): boolean {\n return this.readMeta(LEGACY_JSONL_MIGRATION_KEY) !== undefined;\n }\n\n markLegacyJournalImported(): void {\n this.db\n .prepare(\n `INSERT INTO chronicle_meta (key, value) VALUES (?, 'done')\n ON CONFLICT(key) DO UPDATE SET value = 'done'`,\n )\n .run(LEGACY_JSONL_MIGRATION_KEY);\n }\n\n /**\n * Record the day families the import refused to move.\n *\n * Persisted rather than merely logged because the import runs once: after the\n * marker is set nothing re-reads the JSONL, so this row is the only surviving\n * evidence that a day was dropped. Health reports read it back to say\n * \"degraded, and here is exactly what is missing\" instead of quietly serving\n * a journal with a hole in it.\n */\n recordQuarantinedFamilies(families: readonly ChronicleQuarantinedFamily[]): void {\n if (families.length === 0) return;\n this.db\n .prepare(\n `INSERT INTO chronicle_meta (key, value) VALUES (?, ?)\n ON CONFLICT(key) DO UPDATE SET value = excluded.value`,\n )\n .run(LEGACY_JSONL_QUARANTINE_KEY, JSON.stringify(families));\n }\n\n /**\n * Does this day already hold rows?\n *\n * Each family commits on its own, so an import interrupted between families\n * leaves a database that is complete for the days it reached. `(day,\n * sequence)` is the primary key, so re-inserting one of those days would\n * abort on a constraint violation rather than start over \u2014 this is what lets\n * the next run resume at the first day it never got to.\n */\n hasImportedDay(day: string): boolean {\n const row = this.db.prepare('SELECT 1 AS present FROM events WHERE day = ? LIMIT 1').get(day) as\n | { present: number }\n | undefined;\n return row !== undefined;\n }\n\n /** Day families the legacy import refused to move, oldest first. */\n quarantinedFamilies(): ChronicleQuarantinedFamily[] {\n const raw = this.readMeta(LEGACY_JSONL_QUARANTINE_KEY);\n if (!raw) return [];\n try {\n const parsed: unknown = JSON.parse(raw);\n return Array.isArray(parsed) ? (parsed as ChronicleQuarantinedFamily[]) : [];\n } catch {\n return [];\n }\n }\n\n // \u2500\u2500\u2500 internals \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n private readMeta(key: string): string | undefined {\n const row = this.db.prepare('SELECT value FROM chronicle_meta WHERE key = ?').get(key) as\n | { value: string }\n | undefined;\n return row?.value;\n }\n\n private readCheckpoint(day: string): ChainAnchor | undefined {\n return this.db.prepare('SELECT sequence, hash FROM chain_checkpoint WHERE day = ?').get(day) as\n | ChainAnchor\n | undefined;\n }\n\n /** Days that currently hold at least one event, oldest first. */\n private days(): string[] {\n const rows = this.db.prepare('SELECT DISTINCT day FROM events ORDER BY day').all() as Array<{\n day: string;\n }>;\n return rows.map((row) => row.day);\n }\n\n /**\n * Resolve the chain head, in the same precedence the JSONL journal uses: the\n * newest event, else the retention checkpoint (every event before it was\n * purged), else genesis.\n */\n private readAnchor(day: string): ChainAnchor {\n const cached = this.anchors.get(day);\n if (cached) return cached;\n const last = this.db\n .prepare('SELECT sequence, hash FROM events WHERE day = ? ORDER BY sequence DESC LIMIT 1')\n .get(day) as ChainAnchor | undefined;\n const anchor = last ?? this.readCheckpoint(day) ?? { sequence: 0, hash: GENESIS_HASH };\n this.anchors.set(day, anchor);\n return anchor;\n }\n\n private ensureSchema(): void {\n const version = (this.db.prepare('PRAGMA user_version').get() as { user_version: number })\n .user_version;\n this.db.exec(`\n CREATE TABLE IF NOT EXISTS events (\n day TEXT NOT NULL,\n sequence INTEGER NOT NULL,\n event_id TEXT NOT NULL UNIQUE,\n hash TEXT NOT NULL,\n previous_hash TEXT NOT NULL,\n occurred_at TEXT NOT NULL,\n event_type TEXT NOT NULL,\n outcome TEXT,\n project_id TEXT,\n session_id TEXT,\n agent_id TEXT,\n task_id TEXT,\n trace_id TEXT,\n logical_request_id TEXT,\n resource_kind TEXT,\n resource_id TEXT,\n resource_path TEXT,\n duration_ns TEXT,\n payload TEXT NOT NULL,\n PRIMARY KEY (day, sequence)\n );\n CREATE INDEX IF NOT EXISTS events_occurred_at ON events(occurred_at);\n CREATE INDEX IF NOT EXISTS events_type_outcome ON events(event_type, outcome);\n CREATE INDEX IF NOT EXISTS events_session ON events(session_id, day, sequence);\n CREATE INDEX IF NOT EXISTS events_trace ON events(trace_id);\n CREATE INDEX IF NOT EXISTS events_logical_request ON events(logical_request_id);\n CREATE INDEX IF NOT EXISTS events_resource_path ON events(resource_path);\n\n CREATE TABLE IF NOT EXISTS chain_checkpoint (\n day TEXT PRIMARY KEY,\n sequence INTEGER NOT NULL,\n hash TEXT NOT NULL\n );\n\n CREATE TABLE IF NOT EXISTS chronicle_meta (\n key TEXT PRIMARY KEY,\n value TEXT NOT NULL\n );\n `);\n if (version !== SCHEMA_VERSION) {\n this.db.exec(`PRAGMA user_version = ${SCHEMA_VERSION}`);\n }\n }\n}\n\ninterface ProjectedRow {\n occurredAt: string;\n outcome: string | null;\n projectId: string | null;\n sessionId: string | null;\n agentId: string | null;\n taskId: string | null;\n traceId: string | null;\n logicalRequestId: string | null;\n resourceKind: string | null;\n resourceId: string | null;\n resourcePath: string | null;\n durationNs: string | null;\n}\n\n/**\n * Derive the indexed columns from an event.\n *\n * Every value here is recoverable from `payload`; nothing is stored only in a\n * column. That is what lets the projection change in a later release without\n * touching a single stored hash.\n *\n * `day` is deliberately absent: it is the chain scope, not a projection. The\n * legacy writer picks it from the wall clock when the batch is appended (see\n * `journalForToday`), so an event carrying a back-dated `occurredAt` still\n * belongs to the chain of the day it was written on.\n */\nfunction projectEvent(event: ChronicleEvent): ProjectedRow {\n const occurredAt = event.occurredAt ?? event.observedAt;\n return {\n occurredAt,\n outcome: event.outcome ?? null,\n projectId: event.scope.projectId ?? null,\n sessionId: event.scope.sessionId ?? null,\n agentId: event.scope.agentId ?? null,\n taskId: event.scope.taskId ?? null,\n traceId: event.correlation?.traceId ?? null,\n logicalRequestId: event.correlation?.logicalRequestId ?? null,\n resourceKind: event.resource?.kind ?? null,\n resourceId: event.resource?.id ?? null,\n resourcePath: event.resource?.path ?? null,\n durationNs: event.durationNs ?? null,\n };\n}\n", "/**\n * SQLite read path for Chronicle (phase 3 of `chronicle-sqlite-journal-v1`).\n *\n * The division of labour is the whole point of this file:\n *\n * - **SQL narrows.** Indexed columns turn \"parse every line of every partition\n * that overlaps the range\" into an index seek. Only predicates that map\n * cleanly onto a column are pushed down.\n * - **JavaScript decides.** The pushed-down predicate is a deliberate\n * *superset*: every candidate row is parsed and then passed through the same\n * `matches()` the JSONL engine uses. Nothing is filtered out by SQL that\n * `matches()` would have kept.\n *\n * That split is what makes parity provable rather than hoped for. A SQL\n * re-expression of `ChronicleQuery` would have to restate tag/attribute\n * lookups, path normalisation and line-range containment, and each restatement\n * is a place where the two engines could silently disagree. Here they cannot\n * disagree about *which* events match \u2014 only about how fast the candidates are\n * found.\n *\n * The summary is built with the JSONL engine's own accumulator for the same\n * reason: family classification, `usage.*` paths, cost de-duplication and the\n * p95 are semantics, not arithmetic.\n */\nimport type { DatabaseSync } from 'node:sqlite';\nimport type { ChronicleEvent } from './types.js';\nimport {\n type ChronicleFacet,\n type ChronicleFacetResults,\n type ChronicleFacetValue,\n type ChronicleGraphEdge,\n type ChronicleGraphResult,\n type ChronicleQuery,\n type ChronicleQueryResult,\n compareEvents,\n createSummaryAccumulator,\n facetValue,\n finalizeSummary,\n matches,\n relationKeys,\n updateSummary,\n} from './query.js';\n\n/** Hard ceiling mirroring `ChronicleQueryEngine.query`. */\nconst MAX_LIMIT = 10_000;\n\n/**\n * Keyset position in the `(day, sequence)` total order.\n *\n * Deliberately not interchangeable with the JSONL engine's cursor, which\n * encodes a snapshot of partition files. A cursor is opaque and belongs to the\n * engine that issued it; carrying one across would be meaningless.\n */\ninterface SqliteCursor {\n day: string;\n sequence: number;\n}\n\nfunction encodeCursor(cursor: SqliteCursor): string {\n return Buffer.from(`${cursor.day}:${cursor.sequence}`, 'utf8').toString('base64url');\n}\n\nfunction decodeCursor(raw: string | undefined): SqliteCursor | undefined {\n if (!raw) return undefined;\n try {\n const [day, sequence] = Buffer.from(raw, 'base64url').toString('utf8').split(':');\n if (!day || sequence === undefined) return undefined;\n const parsed = Number(sequence);\n return Number.isSafeInteger(parsed) ? { day, sequence: parsed } : undefined;\n } catch {\n return undefined;\n }\n}\n\ninterface PushedDown {\n clause: string;\n params: (string | number)[];\n}\n\n/**\n * Translate the parts of a query that map onto indexed columns.\n *\n * Anything absent here is simply not narrowed \u2014 `matches()` still applies it.\n * Adding a predicate to this list is an optimization; forgetting one is not a\n * correctness bug. That asymmetry is intentional.\n */\nfunction pushDown(query: ChronicleQuery): PushedDown {\n const clauses: string[] = [];\n const params: (string | number)[] = [];\n\n const eq = (column: string, value: string | undefined): void => {\n if (value === undefined) return;\n clauses.push(`${column} = ?`);\n params.push(value);\n };\n\n eq('event_id', query.eventId);\n eq('project_id', query.projectId);\n eq('session_id', query.sessionId);\n eq('agent_id', query.agentId);\n eq('task_id', query.taskId);\n eq('trace_id', query.traceId);\n eq('logical_request_id', query.logicalRequestId);\n eq('resource_kind', query.resourceKind);\n eq('resource_id', query.resourceId);\n\n if (query.eventTypes?.length) {\n clauses.push(`event_type IN (${query.eventTypes.map(() => '?').join(',')})`);\n params.push(...query.eventTypes);\n }\n if (query.outcomes?.length) {\n clauses.push(`outcome IN (${query.outcomes.map(() => '?').join(',')})`);\n params.push(...query.outcomes);\n }\n // `occurred_at` is an ISO-8601 UTC string, so lexicographic comparison is\n // chronological \u2014 the same assumption `matches()` makes.\n if (query.from) {\n clauses.push('occurred_at >= ?');\n params.push(query.from);\n }\n if (query.to) {\n clauses.push('occurred_at <= ?');\n params.push(query.to);\n }\n\n return { clause: clauses.length ? clauses.join(' AND ') : '1=1', params };\n}\n\nexport interface ChronicleSqliteQueryEngineOptions {\n /** Rows pulled from SQLite per batch while streaming candidates. */\n batchSize?: number | undefined;\n}\n\nexport class ChronicleSqliteQueryEngine {\n readonly diagnostics = { sourceFiles: 1, invalidLines: 0 };\n private readonly batchSize: number;\n\n constructor(\n private readonly db: DatabaseSync,\n options: ChronicleSqliteQueryEngineOptions = {},\n ) {\n this.batchSize = Math.max(1, options.batchSize ?? 1_000);\n }\n\n async query(query: ChronicleQuery = {}): Promise<ChronicleQueryResult> {\n const order = query.order ?? 'desc';\n const limit = Math.max(1, Math.min(query.limit ?? 100, MAX_LIMIT));\n const cursor = decodeCursor(query.cursor);\n const pushed = pushDown(query);\n\n const direction = order === 'asc' ? 'ASC' : 'DESC';\n const comparison = order === 'asc' ? '>' : '<';\n const keyset = cursor ? ` AND (day, sequence) ${comparison} (?, ?)` : '';\n const sql =\n `SELECT day, sequence, payload FROM events WHERE ${pushed.clause}${keyset}` +\n ` ORDER BY day ${direction}, sequence ${direction} LIMIT ? OFFSET ?`;\n\n const summary = createSummaryAccumulator();\n const page: ChronicleEvent[] = [];\n let total = 0;\n let scannedEvents = 0;\n let last: SqliteCursor | undefined;\n let offset = 0;\n\n // Every matching event feeds the summary, which is defined over the whole\n // result set rather than the page (see `ChronicleSummary`). Candidates are\n // streamed in batches so a wide query does not materialise the table.\n for (;;) {\n const params = [...pushed.params];\n if (cursor) params.push(cursor.day, cursor.sequence);\n params.push(this.batchSize, offset);\n const rows = this.db.prepare(sql).all(...params) as Array<{\n day: string;\n sequence: number;\n payload: string;\n }>;\n if (rows.length === 0) break;\n offset += rows.length;\n\n for (const row of rows) {\n scannedEvents++;\n let event: ChronicleEvent;\n try {\n event = JSON.parse(row.payload) as ChronicleEvent;\n } catch {\n this.diagnostics.invalidLines++;\n continue;\n }\n if (!matches(event, query)) continue;\n total++;\n updateSummary(summary, event);\n if (page.length < limit) {\n page.push(event);\n last = { day: row.day, sequence: row.sequence };\n }\n }\n if (rows.length < this.batchSize) break;\n }\n\n // The JSONL engine returns the page in `compareEvents` order; keyset order\n // is `(day, sequence)`, which can differ when events share a timestamp.\n // Sorting here keeps both engines' pages identical.\n page.sort((left, right) => compareEvents(left, right) * (order === 'asc' ? 1 : -1));\n\n const result: ChronicleQueryResult = {\n events: page,\n total,\n scannedEvents,\n sourceFiles: this.diagnostics.sourceFiles,\n invalidLines: this.diagnostics.invalidLines,\n summary: finalizeSummary(summary),\n };\n if (total > page.length && last) {\n return { ...result, nextCursor: encodeCursor(last) };\n }\n return result;\n }\n\n /**\n * Value counts per facet field.\n *\n * Not a SQL `GROUP BY`: `facetValue()` reads fields that live inside the\n * payload \u2014 provider, model, tool call, tag \u2014 so grouping in SQL would only\n * work for the handful that happen to be columns and would need a second,\n * divergent definition for the rest. The narrowing is still done by SQL; the\n * counting uses the JSONL engine's own projection.\n */\n async facets(\n fields: readonly ChronicleFacet[],\n query: ChronicleQuery = {},\n limit = 100,\n ): Promise<ChronicleFacetResults> {\n const uniqueFields = [...new Set(fields)];\n if (uniqueFields.length === 0) return {};\n const counts = new Map(uniqueFields.map((field) => [field, new Map<string, number>()]));\n\n for (const event of this.eachMatch(query)) {\n for (const field of uniqueFields) {\n const value = facetValue(event, field);\n if (value === undefined) continue;\n const fieldCounts = counts.get(field);\n fieldCounts?.set(value, (fieldCounts.get(value) ?? 0) + 1);\n }\n }\n\n const result: ChronicleFacetResults = {};\n for (const field of uniqueFields) {\n result[field] = [...(counts.get(field) ?? new Map<string, number>())]\n .map(([value, count]) => ({ value, count }))\n // Ties broken by value so both engines agree on an otherwise arbitrary\n // order \u2014 the same comparator `ChronicleQueryEngine.facets` uses.\n .sort((left, right) => right.count - left.count || left.value.localeCompare(right.value))\n .slice(0, Math.max(0, limit));\n }\n return result;\n }\n\n async facet(\n field: ChronicleFacet,\n query: ChronicleQuery = {},\n limit = 100,\n ): Promise<ChronicleFacetValue[]> {\n return (await this.facets([field], query, limit))[field] ?? [];\n }\n\n /**\n * Expand explicit and typed correlation edges around a seed set.\n *\n * The traversal is the JSONL engine's, moved onto rows: `relationKeys()`\n * defines the edges, `compareEvents` orders the nodes, and each hop is\n * another ordered pass. Order is load-bearing rather than cosmetic \u2014 both\n * `maxNodes` truncations stop at whatever they reach first, so a differently\n * ordered scan would return a different subgraph rather than the same one\n * shuffled. `ORDER BY day, sequence` reproduces `comparePartitionPaths`\n * (family, then rotation index) followed by line order within a partition.\n */\n async graph(\n seed: ChronicleQuery = {},\n hops = 2,\n maxNodes = 1_000,\n ): Promise<ChronicleGraphResult> {\n const nodeLimit = Math.max(0, Math.floor(maxNodes));\n const selected = new Map<string, ChronicleEvent>();\n let seedCount = 0;\n\n for (const event of this.eachMatch(seed)) {\n seedCount++;\n if (selected.size < nodeLimit) selected.set(event.eventId, event);\n }\n\n let frontier = [...selected.values()];\n const depthLimit = Math.max(0, Math.min(hops, 10));\n for (\n let depth = 0;\n depth < depthLimit && frontier.length > 0 && selected.size < nodeLimit;\n depth++\n ) {\n const frontierKeys = new Set(\n frontier.flatMap((event) => relationKeys(event).map((relation) => relation.key)),\n );\n const next: ChronicleEvent[] = [];\n for (const event of this.eachMatch({})) {\n if (selected.has(event.eventId)) continue;\n if (!relationKeys(event).some((relation) => frontierKeys.has(relation.key))) continue;\n selected.set(event.eventId, event);\n next.push(event);\n if (selected.size >= nodeLimit) break;\n }\n frontier = next;\n }\n\n const nodes = [...selected.values()].sort(compareEvents);\n const byKey = new Map<string, ChronicleEvent[]>();\n for (const node of nodes) {\n for (const relation of relationKeys(node)) {\n const related = byKey.get(relation.key) ?? [];\n related.push(node);\n byKey.set(relation.key, related);\n }\n }\n\n const edges: ChronicleGraphEdge[] = [];\n const seen = new Set<string>();\n for (const node of nodes) {\n for (const relation of relationKeys(node)) {\n for (const candidate of byKey.get(relation.key) ?? []) {\n if (candidate.eventId === node.eventId) continue;\n const [from, to] =\n compareEvents(node, candidate) <= 0 ? [node, candidate] : [candidate, node];\n const id = `${from.eventId}:${to.eventId}:${relation.kind}`;\n if (seen.has(id)) continue;\n seen.add(id);\n edges.push({\n from: from.eventId,\n to: to.eventId,\n kind: relation.kind,\n confidence: relation.confidence,\n });\n }\n }\n }\n\n return {\n nodes,\n edges,\n truncated: seedCount > nodeLimit || selected.size >= nodeLimit,\n };\n }\n\n /** Every event satisfying `query`, pulled in batches so a wide scan stays bounded. */\n private *eachMatch(query: ChronicleQuery): Generator<ChronicleEvent> {\n const pushed = pushDown(query);\n const sql =\n `SELECT payload FROM events WHERE ${pushed.clause}` +\n ' ORDER BY day, sequence LIMIT ? OFFSET ?';\n let offset = 0;\n for (;;) {\n const rows = this.db.prepare(sql).all(...pushed.params, this.batchSize, offset) as Array<{\n payload: string;\n }>;\n if (rows.length === 0) return;\n offset += rows.length;\n for (const row of rows) {\n let event: ChronicleEvent;\n try {\n event = JSON.parse(row.payload) as ChronicleEvent;\n } catch {\n this.diagnostics.invalidLines++;\n continue;\n }\n if (matches(event, query)) yield event;\n }\n if (rows.length < this.batchSize) return;\n }\n }\n}\n", "import { spawn } from 'node:child_process';\nimport * as fs from 'node:fs';\nimport * as net from 'node:net';\nimport * as path from 'node:path';\nimport { fileURLToPath } from 'node:url';\nimport type { ChronicleJournalStats } from './journal.js';\nimport { chronicleProjectServerEndpoint } from './project-server-endpoint.js';\nimport {\n CHRONICLE_PROJECT_SERVER_MAX_FRAME_CHARS,\n CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION,\n type ChronicleProjectServerHealth,\n type ChronicleProjectServerInfo,\n type ChronicleProjectServerMessage,\n type ChronicleServerOperationName,\n type ChronicleServerOperations,\n encodeChronicleProjectServerMessage,\n} from './project-server-protocol.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEvent, ChronicleEventInput } from './types.js';\n\nconst CONNECT_ATTEMPT_TIMEOUT_MS = 750;\nconst SERVER_START_TIMEOUT_MS = 10_000;\nconst DEFAULT_CALL_TIMEOUT_MS = 30_000;\nconst APPEND_CALL_TIMEOUT_MS = 60_000;\nconst DEFAULT_BATCH_WINDOW_MS = 5;\nconst DEFAULT_MAX_PENDING = 100_000;\n\ninterface PendingRequest {\n resolve(value: unknown): void;\n reject(error: unknown): void;\n timer: ReturnType<typeof setTimeout>;\n}\n\nexport interface ChronicleProjectServerClientOptions {\n projectRoot: string;\n globalRoot: string;\n projectId: string;\n projectDir: string;\n workspaceId: string;\n retentionDays?: number | undefined;\n}\n\nexport interface ChronicleProjectServerCallOptions {\n timeoutMs?: number | undefined;\n}\n\n/**\n * Locate the detached Chronicle entry from both regular ESM output and the\n * bundled core entrypoints. In an esbuild bundle `import.meta.url` belongs to\n * the bundle (for example `dist/plugin/index.js`), not this source module, so\n * a single relative lookup silently selects the inline fallback.\n */\n/**\n * Why the Chronicle daemon is or is not usable.\n *\n * `resolveChronicleProjectServerUrl` collapses two very different situations\n * into one `null`: the operator asked for in-process mode, or the built server\n * simply could not be found. Callers that fall back on `null` therefore treat a\n * broken build exactly like a deliberate choice \u2014 and since the lookup is\n * relative to `import.meta.url`, a change in bundle layout alone is enough to\n * silently give every process its own private journal.\n */\nexport type ChronicleDaemonAvailability =\n | { readonly kind: 'available'; readonly url: URL }\n /** `WRONGSTACK_CHRONICLE_INLINE` / `WRONGSTACK_CHRONICLE_SERVER=0` was set. */\n | { readonly kind: 'inline-requested' }\n /** No server entry point exists in any known output layout. */\n | { readonly kind: 'missing-build' };\n\nexport function resolveChronicleDaemonAvailability(\n moduleUrl = import.meta.url,\n exists: (filePath: string) => boolean = fs.existsSync,\n): ChronicleDaemonAvailability {\n if (\n process.env['WRONGSTACK_CHRONICLE_INLINE'] ||\n process.env['WRONGSTACK_CHRONICLE_SERVER'] === '0'\n ) {\n return { kind: 'inline-requested' };\n }\n const url = locateChronicleProjectServer(moduleUrl, exists);\n return url ? { kind: 'available', url } : { kind: 'missing-build' };\n}\n\nexport function resolveChronicleProjectServerUrl(\n moduleUrl = import.meta.url,\n exists: (filePath: string) => boolean = fs.existsSync,\n): URL | null {\n const availability = resolveChronicleDaemonAvailability(moduleUrl, exists);\n return availability.kind === 'available' ? availability.url : null;\n}\n\nfunction locateChronicleProjectServer(\n moduleUrl: string,\n exists: (filePath: string) => boolean,\n): URL | null {\n const candidates = [\n // Normal unbundled output: dist/chronicle/project-server-client.js.\n './project-server.js',\n // Core plugin bundle: dist/plugin/index.js.\n '../chronicle/project-server.js',\n // Core root bundle: dist/index.js.\n './chronicle/project-server.js',\n ];\n for (const relativePath of candidates) {\n try {\n const url = new URL(relativePath, moduleUrl);\n if (url.protocol === 'file:' && exists(fileURLToPath(url))) return url;\n } catch {\n // Try the next known output layout.\n }\n }\n return null;\n}\n\nexport function isChronicleProjectServerAvailable(): boolean {\n return resolveChronicleProjectServerUrl() !== null;\n}\n\nfunction delay(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n\n/**\n * Multiplexed IPC client for the single Chronicle owner of a local project.\n */\nexport class ChronicleProjectServerClient {\n readonly endpoint: string;\n private socket: net.Socket | null = null;\n private info: ChronicleProjectServerInfo | null = null;\n private buffer = '';\n private connecting: Promise<void> | null = null;\n private connectResolve: (() => void) | null = null;\n private connectReject: ((error: unknown) => void) | null = null;\n private nextId = 1;\n private readonly pending = new Map<number, PendingRequest>();\n\n constructor(readonly options: ChronicleProjectServerClientOptions) {\n this.endpoint = chronicleProjectServerEndpoint(options.projectDir);\n }\n\n async call<O extends ChronicleServerOperationName>(\n op: O,\n args: ChronicleServerOperations[O]['args'],\n options: ChronicleProjectServerCallOptions = {},\n ): Promise<ChronicleServerOperations[O]['result']> {\n await this.ensureConnected(true);\n return this.request<ChronicleServerOperations[O]['result']>(\n { type: 'request', op, args },\n options.timeoutMs ?? DEFAULT_CALL_TIMEOUT_MS,\n );\n }\n\n ping(): Promise<ChronicleProjectServerHealth> {\n return this.call('ping', {}, { timeoutMs: 3_000 });\n }\n\n /**\n * Request the Chronicle project server to shut down cleanly.\n *\n * Returns the server PID and acknowledgment. Does not throw if the server\n * is already offline or unreachable \u2014 the caller is assumed to want the\n * server stopped regardless of current state.\n */\n async shutdown(reason?: string): Promise<{ stopped: boolean; pid?: number; reason?: string }> {\n try {\n await this.ensureConnected(false);\n } catch {\n return { stopped: false, reason: 'offline' };\n }\n const pid = this.info?.pid;\n try {\n const result = (await this.request<{ stopped: boolean; pid?: number; reason?: string }>(\n { type: 'shutdown', reason },\n 5_000,\n )) ?? { stopped: true };\n return { ...result, ...(pid !== undefined && result.pid === undefined ? { pid } : {}) };\n } catch {\n return { stopped: false, ...(pid !== undefined ? { pid } : {}), reason: 'write-failed' };\n }\n }\n\n async close(): Promise<void> {\n const socket = this.socket;\n this.socket = null;\n this.info = null;\n if (socket && !socket.destroyed) {\n await new Promise<void>((resolve) => {\n socket.once('close', resolve);\n socket.end();\n });\n }\n }\n\n private async ensureConnected(spawnIfMissing: boolean): Promise<void> {\n if (this.socket && !this.socket.destroyed && this.info) return;\n if (this.connecting) return this.connecting;\n if (!isChronicleProjectServerAvailable()) {\n throw new Error(\n 'Built Chronicle project server is unavailable. Build @wrongstack/core or use the inline journal.',\n );\n }\n this.connecting = this.connectWithElection(spawnIfMissing).finally(() => {\n this.connecting = null;\n });\n return this.connecting;\n }\n\n private async connectWithElection(spawnIfMissing: boolean): Promise<void> {\n const deadline =\n Date.now() + (spawnIfMissing ? SERVER_START_TIMEOUT_MS : CONNECT_ATTEMPT_TIMEOUT_MS);\n let spawned = false;\n let lastError: unknown = new Error('Chronicle project server unavailable');\n while (Date.now() < deadline) {\n try {\n await this.connectOnce();\n return;\n } catch (error) {\n lastError = error;\n }\n if (!spawnIfMissing) break;\n if (!spawned) {\n this.spawnDetachedServer();\n spawned = true;\n }\n await delay(75);\n }\n throw lastError;\n }\n\n private connectOnce(): Promise<void> {\n this.socket?.destroy();\n this.socket = null;\n this.info = null;\n this.buffer = '';\n return new Promise<void>((resolve, reject) => {\n const socket = net.createConnection(this.endpoint);\n this.socket = socket;\n socket.setEncoding('utf8');\n const timer = setTimeout(() => {\n reject(new Error('Chronicle project server handshake timed out'));\n socket.destroy();\n }, CONNECT_ATTEMPT_TIMEOUT_MS);\n timer.unref?.();\n this.connectResolve = () => {\n clearTimeout(timer);\n this.connectResolve = null;\n this.connectReject = null;\n resolve();\n };\n this.connectReject = (error) => {\n clearTimeout(timer);\n this.connectResolve = null;\n this.connectReject = null;\n reject(error);\n };\n socket.on('data', (chunk: string) => this.onData(socket, chunk));\n socket.on('error', (error) => {\n if (!this.info) this.connectReject?.(error);\n });\n socket.on('close', () => this.onClose(socket));\n });\n }\n\n private request<T>(\n message:\n | { type: 'request'; op: ChronicleServerOperationName; args: unknown }\n | { type: 'shutdown'; reason?: string | undefined },\n timeoutMs: number,\n ): Promise<T> {\n const socket = this.socket;\n if (!socket || socket.destroyed) {\n return Promise.reject(new Error('Chronicle project server connection is unavailable'));\n }\n const id = this.nextId++;\n const encoded = encodeChronicleProjectServerMessage({ ...message, id });\n if (encoded.length > CHRONICLE_PROJECT_SERVER_MAX_FRAME_CHARS) {\n return Promise.reject(new Error('Chronicle project server request exceeded frame limit'));\n }\n const label = message.type === 'request' ? message.op : message.type;\n return new Promise<T>((resolve, reject) => {\n const timer = setTimeout(() => {\n const pending = this.pending.get(id);\n if (!pending) return;\n this.pending.delete(id);\n pending.reject(new Error(`Chronicle ${label} exceeded its ${timeoutMs}ms timeout`));\n }, timeoutMs);\n timer.unref?.();\n this.pending.set(id, { resolve, reject, timer });\n socket.write(encoded);\n });\n }\n\n private onData(socket: net.Socket, chunk: string): void {\n if (socket !== this.socket) return;\n this.buffer += chunk;\n if (this.buffer.length > CHRONICLE_PROJECT_SERVER_MAX_FRAME_CHARS) {\n socket.destroy(new Error('Chronicle project server response exceeded frame limit'));\n return;\n }\n while (true) {\n const newline = this.buffer.indexOf('\\n');\n if (newline < 0) return;\n const line = this.buffer.slice(0, newline);\n this.buffer = this.buffer.slice(newline + 1);\n if (!line) continue;\n let message: ChronicleProjectServerMessage;\n try {\n message = JSON.parse(line) as ChronicleProjectServerMessage;\n } catch {\n socket.destroy(new Error('Invalid Chronicle project server response'));\n return;\n }\n this.onMessage(message);\n }\n }\n\n private onMessage(message: ChronicleProjectServerMessage): void {\n if (message.type === 'hello') {\n if (message.protocolVersion !== CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION) {\n this.connectReject?.(\n new Error(\n `Chronicle protocol mismatch: client=${CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION}, server=${message.protocolVersion}`,\n ),\n );\n this.socket?.destroy();\n return;\n }\n if (\n normalizePath(message.projectRoot) !== normalizePath(this.options.projectRoot) ||\n normalizePath(message.projectDir) !== normalizePath(this.options.projectDir)\n ) {\n this.connectReject?.(new Error('Chronicle project server identity mismatch'));\n this.socket?.destroy();\n return;\n }\n this.info = message;\n this.connectResolve?.();\n return;\n }\n const pending = this.pending.get(message.id);\n if (!pending) return;\n this.pending.delete(message.id);\n clearTimeout(pending.timer);\n if (message.ok) pending.resolve(message.result);\n else {\n const error = new Error(message.error);\n if (message.errorName) error.name = message.errorName;\n pending.reject(error);\n }\n }\n\n private onClose(socket: net.Socket): void {\n if (socket !== this.socket) return;\n this.socket = null;\n this.info = null;\n const error = new Error('Chronicle project server connection closed');\n this.connectReject?.(error);\n this.connectResolve = null;\n this.connectReject = null;\n const pending = [...this.pending.values()];\n this.pending.clear();\n for (const request of pending) {\n clearTimeout(request.timer);\n request.reject(error);\n }\n }\n\n private spawnDetachedServer(): void {\n const url = resolveChronicleProjectServerUrl();\n if (!url) throw new Error('Built Chronicle project server is unavailable');\n const args = [\n fileURLToPath(url),\n '--project-root',\n this.options.projectRoot,\n '--global-root',\n this.options.globalRoot,\n '--project-id',\n this.options.projectId,\n '--project-dir',\n this.options.projectDir,\n '--workspace-id',\n this.options.workspaceId,\n ];\n if (this.options.retentionDays !== undefined) {\n args.push('--retention-days', String(this.options.retentionDays));\n }\n const child = spawn(process.execPath, args, {\n detached: true,\n stdio: 'ignore',\n windowsHide: true,\n env: process.env,\n });\n child.unref();\n }\n}\n\ninterface QueuedAppend {\n input: ChronicleEventInput;\n resolve(event: ChronicleEvent): void;\n reject(error: unknown): void;\n}\n\n/**\n * ChronicleEventSink backed by the project server. A short client-side batch\n * window keeps high-frequency EventBus adapters from turning into one IPC\n * round trip per event.\n */\nexport class ChronicleRemoteJournal implements ChronicleEventSink {\n private readonly client: ChronicleProjectServerClient;\n private readonly maxPending: number;\n private readonly batchWindowMs: number;\n private pending: QueuedAppend[] = [];\n private timer: ReturnType<typeof setTimeout> | undefined;\n private readonly inflight = new Set<Promise<void>>();\n private readonly counters = {\n acceptedEvents: 0,\n persistedEvents: 0,\n rejectedEvents: 0,\n failedEvents: 0,\n batches: 0,\n maxObservedPending: 0,\n largestBatch: 0,\n partitionRolls: 0,\n };\n private lastBatchDurationMs: number | undefined;\n\n constructor(\n options: ChronicleProjectServerClientOptions & {\n maxPending?: number | undefined;\n batchWindowMs?: number | undefined;\n },\n client = new ChronicleProjectServerClient(options),\n ) {\n this.client = client;\n this.maxPending = Math.max(1, options.maxPending ?? DEFAULT_MAX_PENDING);\n this.batchWindowMs = Math.max(0, options.batchWindowMs ?? DEFAULT_BATCH_WINDOW_MS);\n }\n\n append(input: ChronicleEventInput): Promise<ChronicleEvent> {\n if (this.pending.length >= this.maxPending) {\n this.counters.rejectedEvents++;\n return Promise.reject(\n new Error(`Chronicle backpressure limit reached (${this.maxPending} pending events)`),\n );\n }\n const promise = new Promise<ChronicleEvent>((resolve, reject) => {\n this.pending.push({ input, resolve, reject });\n });\n this.counters.acceptedEvents++;\n this.counters.maxObservedPending = Math.max(\n this.counters.maxObservedPending,\n this.pending.length,\n );\n this.schedule();\n return promise;\n }\n\n stats(): ChronicleJournalStats {\n return {\n ...this.counters,\n pendingEvents: this.pending.length,\n ...(this.lastBatchDurationMs !== undefined\n ? { lastBatchDurationMs: this.lastBatchDurationMs }\n : {}),\n };\n }\n\n async flush(): Promise<void> {\n if (this.timer) {\n clearTimeout(this.timer);\n this.timer = undefined;\n }\n while (this.pending.length > 0 || this.inflight.size > 0) {\n if (this.pending.length > 0) this.startBatch();\n await Promise.all([...this.inflight]);\n }\n if (this.counters.acceptedEvents === 0) return;\n await this.client.call('flush', {}, { timeoutMs: APPEND_CALL_TIMEOUT_MS });\n }\n\n async dispose(): Promise<void> {\n await this.flush();\n await this.client.close();\n }\n\n private schedule(): void {\n if (this.timer) return;\n if (this.batchWindowMs === 0) {\n queueMicrotask(() => this.startBatch());\n return;\n }\n this.timer = setTimeout(() => {\n this.timer = undefined;\n this.startBatch();\n }, this.batchWindowMs);\n this.timer.unref?.();\n }\n\n private startBatch(): void {\n if (this.timer) {\n clearTimeout(this.timer);\n this.timer = undefined;\n }\n if (this.pending.length === 0) return;\n const batch = this.pending.splice(0);\n const started = performance.now();\n this.counters.batches++;\n this.counters.largestBatch = Math.max(this.counters.largestBatch, batch.length);\n const run = this.client\n .call(\n 'append',\n { inputs: batch.map((entry) => entry.input) },\n { timeoutMs: APPEND_CALL_TIMEOUT_MS },\n )\n .then((events) => {\n if (events.length !== batch.length) {\n throw new Error(\n `Chronicle server returned ${events.length} events for ${batch.length} inputs`,\n );\n }\n batch.forEach((entry, index) => {\n entry.resolve(events[index]!);\n });\n this.counters.persistedEvents += batch.length;\n })\n .catch((error) => {\n this.counters.failedEvents += batch.length;\n for (const entry of batch) entry.reject(error);\n })\n .finally(() => {\n this.lastBatchDurationMs = performance.now() - started;\n this.inflight.delete(run);\n if (this.pending.length > 0) this.schedule();\n });\n this.inflight.add(run);\n }\n}\n\nfunction normalizePath(value: string): string {\n const resolved = path.resolve(value);\n return process.platform === 'win32' ? resolved.toLowerCase() : resolved;\n}\n", "import { createHash } from 'node:crypto';\nimport * as fs from 'node:fs';\nimport * as os from 'node:os';\nimport * as path from 'node:path';\nimport { assertUnixSocketPathWithinLimit } from '../utils/socket-path.js';\nimport { CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION } from './project-server-protocol.js';\n\nexport const CHRONICLE_PROJECT_SERVER_METADATA_FILE = 'server.json';\n\nfunction normalizedPath(value: string): string {\n const resolved = path.resolve(value);\n return process.platform === 'win32' ? resolved.toLowerCase() : resolved;\n}\n\nexport function chronicleProjectServerKey(projectDir: string): string {\n return createHash('sha256')\n .update(normalizedPath(path.join(projectDir, 'chronicle')))\n .digest('hex')\n .slice(0, 24);\n}\n\n/**\n * Deterministic per-project chronicle IPC endpoint.\n *\n * The Unix subdirectory is the short `wsch-v<V>/` (was\n * `wrongstack-chronicle-v<V>/`, which left a single byte of macOS `sun_path`\n * headroom under the ~48-byte per-user TMPDIR \u2014 see the codebase-index macOS\n * incident and `@wrongstack/persistence` socket-path helpers). ~86 bytes\n * worst-case macOS now.\n *\n * Migration: the protocol version stays embedded in the path, so this rename\n * behaves exactly like a protocol bump \u2014 old daemons keep listening on the old\n * `wrongstack-chronicle-v<V>/` path, are never contacted again, and exit on\n * their idle timeout. No coexistence window: a client build always talks only\n * to the endpoint scheme it derives. Bump\n * `CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION` for wire changes as before; the\n * prefix itself must not grow without re-checking the byte budget.\n * The Windows pipe name keeps the long prefix \u2014 named pipes have no\n * `sun_path` limit.\n */\nexport function chronicleProjectServerEndpoint(projectDir: string): string {\n const key = chronicleProjectServerKey(projectDir);\n if (process.platform === 'win32') {\n return `\\\\\\\\.\\\\pipe\\\\wrongstack-chronicle-v${CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION}-${key}`;\n }\n return path.join(\n os.tmpdir(),\n `wsch-v${CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION}`,\n `${key}.sock`,\n );\n}\n\nexport function chronicleProjectServerMetadataPath(projectDir: string): string {\n return path.join(projectDir, 'chronicle', CHRONICLE_PROJECT_SERVER_METADATA_FILE);\n}\n\nexport function ensureChronicleProjectServerSocketDirectory(endpoint: string): void {\n if (process.platform !== 'win32') {\n // ~86 bytes under a canonical macOS TMPDIR since the wsch-v1/ rename.\n // Assert so growth fails loudly instead of as a silent bind error in the\n // detached daemon (see the codebase-index macOS incident).\n assertUnixSocketPathWithinLimit(endpoint, 'chronicle');\n fs.mkdirSync(path.dirname(endpoint), { recursive: true, mode: 0o700 });\n }\n}\n", "import type { ChronicleJournalStats, ChroniclePurgeResult } from './journal.js';\nimport type { ChronicleMetricsRefreshResult } from './metrics-store.js';\nimport type {\n ChronicleFacet,\n ChronicleFacetResults,\n ChronicleFacetValue,\n ChronicleGraphResult,\n ChronicleQuery,\n ChronicleQueryResult,\n} from './query.js';\nimport type { ChronicleEvent, ChronicleEventInput } from './types.js';\n\nexport const CHRONICLE_PROJECT_SERVER_PROTOCOL_VERSION = 2;\nexport const CHRONICLE_PROJECT_SERVER_MAX_FRAME_CHARS = 64 * 1024 * 1024;\n\nexport interface ChronicleProjectServerInfo {\n protocolVersion: number;\n pid: number;\n projectRoot: string;\n projectDir: string;\n chronicleDirectory: string;\n endpoint: string;\n startedAt: string;\n}\n\nexport interface ChronicleProjectServerHealth extends ChronicleProjectServerInfo {\n checkedAt: number;\n uptimeMs: number;\n clients: number;\n activeRequests: number;\n journal: ChronicleJournalStats;\n watcher: {\n active: boolean;\n watchedFiles: number;\n lastError?: string | undefined;\n };\n /**\n * Day families the legacy JSONL import refused to move for a broken chain.\n *\n * Present and non-empty means the journal has a known hole: those days were\n * never imported and never will be. Health surfaces it as degraded rather\n * than healthy \u2014 a store that silently serves an incomplete audit record is\n * worse than one that says which day is missing.\n */\n quarantinedFamilies?: Array<{ day: string; sequence: number; reason: string }> | undefined;\n memory: {\n rss: number;\n heapUsed: number;\n heapTotal: number;\n external: number;\n };\n}\n\nexport type ChronicleMetricsView = 'summary' | 'providers' | 'tasks' | 'files';\n\nexport interface ChronicleMetricsRequest {\n view: ChronicleMetricsView;\n /**\n * When false, serve the current derived projection immediately and refresh\n * it in the background. Latency-sensitive enrichment must not wait for a\n * multi-GB historical backlog to be indexed.\n */\n refresh?: boolean;\n providers?: { from?: string; to?: string };\n tasks?: {\n runId?: string;\n boardId?: string;\n sessionId?: string;\n status?: string;\n limit?: number;\n };\n files?: {\n path?: string;\n paths?: string[];\n latestPerPath?: boolean;\n taskId?: string;\n boardId?: string;\n sessionId?: string;\n limit?: number;\n };\n}\n\nexport interface ChronicleMetricsResponse {\n refreshed: ChronicleMetricsRefreshResult;\n data: unknown;\n}\n\nexport interface ChronicleServerOperations {\n ping: { args: Record<string, never>; result: ChronicleProjectServerHealth };\n append: { args: { inputs: ChronicleEventInput[] }; result: ChronicleEvent[] };\n flush: { args: Record<string, never>; result: void };\n purge: {\n args: { retentionDays: number; dryRun?: boolean };\n result: ChroniclePurgeResult;\n };\n query: { args: { query: ChronicleQuery }; result: ChronicleQueryResult };\n facet: {\n args: { field: ChronicleFacet; query: ChronicleQuery; limit?: number | undefined };\n result: {\n values: ChronicleFacetValue[];\n diagnostics: { sourceFiles: number; invalidLines: number };\n };\n };\n facets: {\n args: { fields: ChronicleFacet[]; query: ChronicleQuery; limit?: number | undefined };\n result: {\n values: ChronicleFacetResults;\n diagnostics: { sourceFiles: number; invalidLines: number };\n };\n };\n graph: {\n args: { seed: ChronicleQuery; hops?: number | undefined; maxNodes?: number | undefined };\n result: ChronicleGraphResult;\n };\n metrics: { args: ChronicleMetricsRequest; result: ChronicleMetricsResponse };\n}\n\nexport type ChronicleServerOperationName = keyof ChronicleServerOperations;\n\nexport type ChronicleProjectServerClientMessage =\n | {\n type: 'request';\n id: number;\n op: ChronicleServerOperationName;\n args: unknown;\n }\n | { type: 'shutdown'; id: number; reason?: string | undefined };\n\nexport type ChronicleProjectServerMessage =\n | ({ type: 'hello' } & ChronicleProjectServerInfo)\n | { type: 'response'; id: number; ok: true; result: unknown }\n | {\n type: 'response';\n id: number;\n ok: false;\n error: string;\n errorName?: string | undefined;\n };\n\nexport function encodeChronicleProjectServerMessage(message: object): string {\n return `${JSON.stringify(message)}\\n`;\n}\n", "import type { EventBus, EventMap } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleProviderAdapterOptions {\n events: EventBus;\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\n/** Persist provider attempt facts without coupling the provider runner to storage. */\nexport function wireProviderAttemptsToChronicle(options: ChronicleProviderAdapterOptions): () => void {\n // The tool roster rarely changes between attempts, yet its full name list\n // (100+ entries, several KB) used to be re-embedded in every\n // provider.attempt.started manifest. Persist the names once per tools\n // manifestHash; later attempts keep the hash as a back-reference.\n const seenToolManifests = new Set<string>();\n const unsubs = [\n options.events.on('provider.attempt.started', (event) => persist(options, event, {\n eventType: 'provider.attempt.started',\n outcome: 'started',\n occurredAt: event.startedAt,\n }, seenToolManifests)),\n options.events.on('provider.attempt.completed', (event) => persist(options, event, {\n eventType: 'provider.attempt.completed',\n outcome: 'success',\n occurredAt: event.endedAt,\n durationNs: millisecondsToNanoseconds(event.durationMs),\n })),\n options.events.on('provider.attempt.failed', (event) => persist(options, event, {\n eventType: 'provider.attempt.failed',\n outcome: 'failure',\n occurredAt: event.endedAt,\n durationNs: millisecondsToNanoseconds(event.durationMs),\n })),\n ];\n return () => unsubs.forEach((unsubscribe) => { unsubscribe(); });\n}\n\ntype ProviderAttemptEvent =\n | EventMap['provider.attempt.started']\n | EventMap['provider.attempt.completed']\n | EventMap['provider.attempt.failed'];\n\nfunction persist(\n options: ChronicleProviderAdapterOptions,\n event: ProviderAttemptEvent,\n base: Pick<ChronicleEventInput, 'eventType' | 'outcome' | 'occurredAt' | 'durationNs'>,\n seenToolManifests?: Set<string>,\n): void {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const input: ChronicleEventInput = {\n ...base,\n scope: {\n ...context.scope,\n sessionId: event.sessionId,\n ...(event.agentId ? { agentId: event.agentId } : {}),\n ...(event.taskId ? { taskId: event.taskId } : {}),\n ...(event.boardId ? { kanbanBoardId: event.boardId } : {}),\n },\n correlation: {\n ...context.correlation,\n ...(event.traceId ? { traceId: event.traceId } : {}),\n logicalRequestId: event.logicalRequestId,\n attemptId: event.attemptId,\n },\n runtime: { providerId: event.providerId, modelId: event.model },\n attributes: providerAttributes(event, seenToolManifests),\n };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n}\n\nfunction providerAttributes(\n event: ProviderAttemptEvent,\n seenToolManifests?: Set<string>,\n): Record<string, unknown> {\n const { sessionId: _sessionId, traceId: _traceId, agentId: _agentId, providerId: _providerId,\n model: _model, logicalRequestId: _logicalRequestId, attemptId: _attemptId, ...rest } = event;\n const attributes = rest as Record<string, unknown>;\n if (seenToolManifests && isManifest(attributes['promptManifest'])) {\n // Never mutate the bus payload \u2014 other subscribers observe the same object.\n attributes['promptManifest'] = compactManifest(attributes['promptManifest'], seenToolManifests);\n }\n return attributes;\n}\n\n/** Per-message summaries beyond this count carry no marginal evidence \u2014 the\n * manifestId already commits to the full prompt content. */\nconst MANIFEST_MESSAGE_TAIL = 8;\nconst SEEN_TOOL_MANIFEST_CAP = 256;\n\nfunction isManifest(value: unknown): value is Record<string, unknown> {\n return Boolean(value && typeof value === 'object' && !Array.isArray(value));\n}\n\nfunction compactManifest(\n manifest: Record<string, unknown>,\n seenToolManifests: Set<string>,\n): Record<string, unknown> {\n const compacted = { ...manifest };\n const tools = compacted['tools'];\n if (isManifest(tools) && typeof tools['manifestHash'] === 'string') {\n const manifestHash = tools['manifestHash'];\n if (seenToolManifests.has(manifestHash)) {\n const { names: _names, ...toolsWithoutNames } = tools;\n compacted['tools'] = { ...toolsWithoutNames, namesRef: manifestHash };\n } else {\n if (seenToolManifests.size >= SEEN_TOOL_MANIFEST_CAP) seenToolManifests.clear();\n seenToolManifests.add(manifestHash);\n }\n }\n const messages = compacted['messages'];\n if (Array.isArray(messages) && messages.length > MANIFEST_MESSAGE_TAIL) {\n compacted['messages'] = messages.slice(-MANIFEST_MESSAGE_TAIL);\n compacted['messagesTruncated'] = messages.length - MANIFEST_MESSAGE_TAIL;\n }\n return compacted;\n}\n\nfunction millisecondsToNanoseconds(durationMs: number): string {\n return Math.round(durationMs * 1_000_000).toString();\n}\n", "import { createHash } from 'node:crypto';\nimport type { EventBus, EventMap } from '../kernel/events.js';\nimport type { SecretScrubber } from '../types/secret-scrubber.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput, ChronicleResourceRef } from './types.js';\n\nexport interface ChronicleToolAdapterOptions {\n events: EventBus;\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n scrubber: SecretScrubber;\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\n/** Maximum bytes of tool input/output text persisted as a preview. The hash\n * and byte/token counts already capture identity; the full payload is\n * redundant for analytics and dominated journal bytes for read-heavy tools. */\nconst PREVIEW_MAX_BYTES = 2048;\n\n/** Persist the complete tool lifecycle. Resource edges discovered in results\n * (files/symbols/commands touched) are windowed by rollup-adapter.ts instead\n * of persisted raw here. */\nexport function wireToolsToChronicle(options: ChronicleToolAdapterOptions): () => void {\n const unsubs = [\n options.events.on('tool.started', (event) => {\n const input = scrubValue(options.scrubber, event.input);\n persist(options, event, {\n eventType: 'tool.started',\n outcome: 'started',\n attributes: {\n toolName: event.name,\n input: capPreview(input),\n inputHash: hashText(input),\n inputBytes: Buffer.byteLength(input),\n },\n });\n }),\n options.events.on('permission.evaluated', (event) => {\n persist(options, event, {\n eventType: 'permission.evaluated',\n outcome: event.effectiveDecision === 'deny' ? 'denied' : 'success',\n attributes: {\n toolName: event.name,\n inputHash: event.inputHash,\n policyDecision: event.policyDecision,\n effectiveDecision: event.effectiveDecision,\n decisionSource: event.decisionSource,\n reason: event.reason ? options.scrubber.scrub(event.reason) : undefined,\n riskTier: event.riskTier,\n yoloEnabled: event.yoloEnabled,\n boundaryDecision: event.boundaryDecision,\n boundaryReason: event.boundaryReason\n ? options.scrubber.scrub(event.boundaryReason)\n : undefined,\n capabilityDowngraded: event.capabilityDowngraded,\n },\n });\n }),\n options.events.on('tool.executed', (event) => {\n const output = options.scrubber.scrub(event.output ?? '');\n persist(options, event, {\n eventType: 'tool.executed',\n outcome: event.ok ? 'success' : 'failure',\n durationNs: millisecondsToNanoseconds(event.durationMs),\n attributes: {\n toolName: event.name,\n ok: event.ok,\n outputPreview: capPreview(output),\n outputHash: hashText(output),\n outputBytes: event.outputBytes,\n outputTokens: event.outputTokens,\n outputLines: event.outputLines,\n metadata: event.metadata,\n },\n });\n }),\n options.events.on('tool.failed', (event) => persist(options, event, {\n eventType: 'tool.failed',\n outcome: 'failure',\n durationNs: millisecondsToNanoseconds(event.durationMs),\n attributes: {\n toolName: event.name,\n category: event.category,\n retryable: event.retryable,\n detail: event.detail,\n errorCode: event.errorCode,\n errorSubsystem: event.errorSubsystem,\n errorSeverity: event.errorSeverity,\n },\n })),\n options.events.on('tool.progress', (event) => {\n if (event.event.type !== 'file_changed') return;\n const resource = progressResource(event);\n persist(options, event, {\n eventType: 'file.mutation.observed',\n outcome: 'started',\n ...(resource ? { resource } : {}),\n attributes: {\n toolName: event.name,\n progressType: event.event.type,\n text: capPreview(options.scrubber.scrub(event.event.text ?? '')),\n data: capPreview(scrubValue(options.scrubber, event.event.data)),\n operation: event.event.operation,\n },\n });\n }),\n ];\n return () => unsubs.forEach((unsubscribe) => { unsubscribe(); });\n}\n\ntype ToolCorrelationEvent = {\n sessionId?: string | undefined;\n traceId?: string | undefined;\n agentId?: string | undefined;\n id?: string | undefined;\n name: string;\n taskId?: string | undefined;\n boardId?: string | undefined;\n provider?: string | undefined;\n model?: string | undefined;\n};\n\nfunction persist(\n options: ChronicleToolAdapterOptions,\n event: ToolCorrelationEvent,\n fields: Pick<ChronicleEventInput, 'eventType' | 'outcome'> &\n Partial<Pick<ChronicleEventInput, 'durationNs' | 'resource' | 'attributes'>>,\n): void {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const input: ChronicleEventInput = {\n ...fields,\n scope: {\n ...context.scope,\n ...(event.sessionId ? { sessionId: event.sessionId } : {}),\n ...(event.agentId ? { agentId: event.agentId } : {}),\n ...(event.taskId ? { taskId: event.taskId } : {}),\n ...(event.boardId ? { kanbanBoardId: event.boardId } : {}),\n },\n correlation: {\n ...context.correlation,\n ...(event.traceId ? { traceId: event.traceId } : {}),\n ...(event.id ? { toolCallId: event.id } : {}),\n },\n ...(event.provider || event.model\n ? {\n runtime: {\n ...(event.provider ? { providerId: event.provider } : {}),\n ...(event.model ? { modelId: event.model } : {}),\n },\n }\n : {}),\n };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n}\n\nfunction progressResource(event: EventMap['tool.progress']): ChronicleResourceRef | undefined {\n if (event.event.type !== 'file_changed' || !event.event.path) return undefined;\n return {\n kind: 'file',\n id: resourceId('file', event.event.path),\n path: event.event.path,\n ...(event.event.line !== undefined ? { lineStart: event.event.line } : {}),\n ...(event.event.endLine !== undefined ? { lineEnd: event.event.endLine } : {}),\n };\n}\n\nfunction scrubValue(scrubber: SecretScrubber, value: unknown): string {\n if (value === undefined) return '';\n try {\n return scrubber.scrub(JSON.stringify(value));\n } catch {\n return scrubber.scrub(String(value));\n }\n}\n\nfunction resourceId(kind: string, value: string): string {\n return `${kind}_${hashText(value).slice(0, 24)}`;\n}\n\nfunction hashText(value: string): string {\n return createHash('sha256').update(value).digest('hex');\n}\n\n/** Return the string as-is when within the byte budget; otherwise return a\n * `{ preview, truncated, totalBytes }` summary. The hash (always computed on\n * the full value) preserves identity for large payloads. */\nfunction capPreview(value: string): string | { preview: string; truncated: true; totalBytes: number } {\n // Fast path: short strings need only a cheap byteLength check for multibyte safety.\n if (value.length <= PREVIEW_MAX_BYTES) {\n if (Buffer.byteLength(value, 'utf8') <= PREVIEW_MAX_BYTES) return value;\n }\n // Over (or possibly over) budget: encode once \u2014 buf.length is the authoritative byte count.\n const buf = Buffer.from(value, 'utf8');\n if (buf.length <= PREVIEW_MAX_BYTES) return value;\n // Walk back to the nearest valid UTF-8 character boundary.\n let end = PREVIEW_MAX_BYTES;\n while (end > 0 && (buf[end]! & 0xC0) === 0x80) end--;\n return { preview: buf.subarray(0, end).toString('utf8'), truncated: true, totalBytes: buf.length };\n}\n\nfunction millisecondsToNanoseconds(durationMs: number): string {\n return Math.round(durationMs * 1_000_000).toString();\n}\n", "import { createHash } from 'node:crypto';\nimport type { EventBus, EventMap } from '../kernel/events.js';\nimport type { SecretScrubber } from '../types/secret-scrubber.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleProcessAdapterOptions {\n events: EventBus;\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n scrubber: SecretScrubber;\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\nexport function wireProcessesToChronicle(options: ChronicleProcessAdapterOptions): () => void {\n const unsubs = [\n options.events.on('process.started', (event) => persist(options, event, {\n eventType: 'process.started',\n outcome: 'started',\n occurredAt: event.startedAt,\n attributes: {\n command: options.scrubber.scrub(event.command),\n args: event.args.map((arg) => options.scrubber.scrub(arg)),\n cwd: event.cwd,\n parentPid: event.parentPid,\n background: event.background,\n },\n })),\n options.events.on('process.completed', (event) => persist(options, event, {\n eventType: 'process.completed',\n outcome: event.exitCode === 0 ? 'success' : event.timedOut ? 'cancelled' : 'failure',\n occurredAt: event.endedAt,\n durationNs: Math.round(event.durationMs * 1_000_000).toString(),\n attributes: {\n exitCode: event.exitCode,\n signal: event.signal,\n stdoutBytes: event.stdoutBytes,\n stderrBytes: event.stderrBytes,\n timedOut: event.timedOut,\n },\n })),\n ];\n return () => unsubs.forEach((unsubscribe) => { unsubscribe(); });\n}\n\ntype ProcessEvent =\n | EventMap['process.started']\n | EventMap['process.completed'];\n\nfunction persist(\n options: ChronicleProcessAdapterOptions,\n event: ProcessEvent,\n fields: Pick<ChronicleEventInput, 'eventType' | 'outcome' | 'occurredAt'> &\n Partial<Pick<ChronicleEventInput, 'durationNs' | 'attributes'>>,\n): void {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const processKey = `${event.sessionId}\\0${event.pid ?? 'unknown'}\\0${event.toolCallId}`;\n const input: ChronicleEventInput = {\n ...fields,\n scope: {\n ...context.scope,\n sessionId: event.sessionId,\n ...(event.agentId ? { agentId: event.agentId } : {}),\n },\n correlation: {\n ...context.correlation,\n ...(event.traceId ? { traceId: event.traceId } : {}),\n toolCallId: event.toolCallId,\n },\n runtime: {\n ...(event.pid !== undefined ? { processId: event.pid } : {}),\n ...('parentPid' in event ? { parentProcessId: event.parentPid } : {}),\n },\n resource: {\n kind: 'process',\n id: `process_${createHash('sha256').update(processKey).digest('hex').slice(0, 24)}`,\n },\n };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n}\n", "import { monitorEventLoopDelay, performance } from 'node:perf_hooks';\nimport type { EventBus } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\n\nexport interface ChronicleHealthMonitorOptions {\n events: EventBus;\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n intervalMs?: number | undefined;\n onPersistError?: ((error: unknown) => void) | undefined;\n}\n\n/**\n * Low-frequency self-observation proving that telemetry is not starving the\n * runtime. Emitted on the EventBus rather than appended to Chronicle\n * directly \u2014 rollup-adapter.ts windows it into one bounded `metrics.rollup`\n * event instead of one raw event per sample.\n */\nexport function startChronicleHealthMonitor(options: ChronicleHealthMonitorOptions): () => void {\n const intervalMs = Math.max(5_000, options.intervalMs ?? 30_000);\n const delay = monitorEventLoopDelay({ resolution: 20 });\n delay.enable();\n let previousCpu = process.cpuUsage();\n let previousElu = performance.eventLoopUtilization();\n\n const sample = (): void => {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const memory = process.memoryUsage();\n const cpu = process.cpuUsage(previousCpu);\n previousCpu = process.cpuUsage();\n const elu = performance.eventLoopUtilization(previousElu);\n previousElu = performance.eventLoopUtilization();\n const journalBeforeSample = options.journal.stats();\n try {\n options.events.emit('runtime.health.sampled', {\n sessionId: context.scope.sessionId,\n uptimeSeconds: process.uptime(),\n eventLoop: { utilization: elu.utilization, activeMs: elu.active, idleMs: elu.idle,\n delayMeanMs: Number(delay.mean) / 1e6, delayP95Ms: Number(delay.percentile(95)) / 1e6,\n delayMaxMs: Number(delay.max) / 1e6 },\n cpu: { userMicros: cpu.user, systemMicros: cpu.system },\n memory: { rssBytes: memory.rss, heapTotalBytes: memory.heapTotal,\n heapUsedBytes: memory.heapUsed, externalBytes: memory.external, arrayBuffersBytes: memory.arrayBuffers },\n chronicle: journalBeforeSample,\n });\n } catch (error) {\n options.onPersistError?.(error);\n }\n delay.reset();\n };\n\n const timer = setInterval(sample, intervalMs);\n timer.unref?.();\n return () => { clearInterval(timer); delay.disable(); };\n}\n", "import { createHash } from 'node:crypto';\nimport type { BrainDecision, BrainDecisionRequest } from '../coordination/brain.js';\nimport type { EventBus } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleDecisionAdapterOptions {\n events: EventBus; journal: ChronicleEventSink; context: ChronicleContext | (() => ChronicleContext);\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\n/** Decision provenance without persisting raw questions, context or rationale. */\nexport function wireDecisionsToChronicle(options: ChronicleDecisionAdapterOptions): () => void {\n const write = (eventType: string, at: number, sessionId: string | undefined, requestId: string,\n attributes: Record<string, unknown>, outcome: ChronicleEventInput['outcome']): void => {\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const input: ChronicleEventInput = { eventType, occurredAt: new Date(at).toISOString(), outcome,\n scope: { ...context.scope, ...(sessionId ? { sessionId } : {}) }, correlation: context.correlation,\n resource: { kind: 'other', id: `decision:${requestId}` }, attributes: { decisionId: requestId, ...attributes } };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n };\n const requestAttrs = (request: BrainDecisionRequest) => ({ source: request.source, risk: request.risk,\n fallback: request.fallback, questionHash: hash(request.question), contextHash: hash(request.context),\n optionCount: request.options?.length ?? 0,\n options: request.options?.map((option) => ({ id: option.id, risk: option.risk,\n recommended: option.recommended ?? false, labelHash: hash(option.label), consequenceHash: hash(option.consequence) })) });\n const decisionAttrs = (decision: BrainDecision) => ({ type: decision.type,\n ...('optionId' in decision && decision.optionId ? { optionId: decision.optionId } : {}),\n contentHash: hash('text' in decision ? decision.text : 'prompt' in decision ? decision.prompt : decision.reason),\n rationaleHash: hash('rationale' in decision ? decision.rationale : undefined) });\n\n const offs = [\n options.events.on('brain.decision_requested', (e) => write('decision.requested', e.at, e.sessionId, e.request.id, requestAttrs(e.request), 'started')),\n options.events.on('brain.decision_answered', (e) => write('decision.resolved', e.at, e.sessionId, e.request.id, { ...requestAttrs(e.request), ...decisionAttrs(e.decision), resolver: 'brain' }, 'success')),\n options.events.on('brain.decision_ask_human', (e) => write('decision.escalated', e.at, e.sessionId, e.request.id, { ...requestAttrs(e.request), ...decisionAttrs(e.decision) }, 'started')),\n options.events.on('brain.decision_denied', (e) => write('decision.denied', e.at, e.sessionId, e.request.id, { ...requestAttrs(e.request), ...decisionAttrs(e.decision) }, 'denied')),\n options.events.on('brain.human_answered', (e) => write('decision.human_answered', e.at, e.sessionId, e.id, { resolver: 'human', optionId: e.optionId, denied: e.deny ?? false, answerHash: hash(e.text) }, e.deny ? 'denied' : 'success')),\n options.events.on('brain.outcome', (e) => write('decision.outcome_observed', e.at, e.sessionId, e.requestId, { observedOutcome: e.outcome, detailHash: hash(e.detail) }, e.outcome)),\n ];\n return () => offs.forEach((off) => { off(); });\n}\n\nfunction hash(value: string | undefined): string | undefined {\n return value ? createHash('sha256').update(value).digest('hex') : undefined;\n}\n", "import { createHash } from 'node:crypto';\nimport type { EventBus } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput, ChronicleOutcome, ChronicleResourceRef } from './types.js';\n\nexport interface ChronicleDomainAdapterOptions {\n events: EventBus; journal: ChronicleEventSink; context: ChronicleContext | (() => ChronicleContext);\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\n// Events owned by specialized adapters or windowed by the rollup adapter.\n// One regex test replaces 15 individual pattern tests per EventBus emission.\n// Alternatives ending with a literal dollar sign anchor are exact matches;\n// others are prefix matches (same semantics as the original array).\n// prettier-ignore\nconst SPECIALIZED_RE = /^(?:provider\\.attempt\\.|tool\\.|process\\.|brain\\.decision_|brain\\.human_answered$|brain\\.outcome$|file\\.activity$|provider\\.(?:text_delta|thinking_delta)$|ctx\\.pct$|subagent\\.ctx_pct$|countdown\\.tick$|coordinator\\.stats$|session\\.agents_updated$|network\\.request\\.(?:started|completed)$|runtime\\.health\\.sampled$|provider\\.tool_use_(?:start|stop)$)/;\n/**\n * Only domains that can improve coding decisions, provenance, reliability or\n * resource/cost control belong in Chronicle. UI presence, navigation and other\n * product-engagement events are intentionally not captured by this bridge.\n */\n// prettier-ignore\nconst CODING_SIGNAL_RE = /^(?:(?:agent|subagent|delegate|fleet|session|iteration|context|compaction|checkpoint|in_flight|memory|storage|trust|sdd|worktree|kanban|brain|token|budget|concurrency|provider|mcp|network)\\.|file\\.event$|error$)/;\nconst SENSITIVE_KEY = /(content|text|prompt|question|rationale|reason|detail|summary|description|context|input|output|error|message|secret|token|password|key)$/i;\nconst PRESERVE_STRING_KEY = /(^|_)(id|status|state|kind|type|source|model|provider|phase|risk|fallback|path|name|role|sha|branch|mode)$/i;\n/** Known metadata arrays that carry unbounded accumulated state (mail, tool\n * history, commands). Chronicle only needs the most recent entries. */\nconst TRUNCATED_ARRAYS = new Set(['recentMail', 'recentTools', 'recentCommands', 'activated', 'injected']);\nconst TRUNCATED_ARRAY_MAX = 5;\n/** General array cap \u2014 enough for agent lists, file lists etc. without\n * allowing unbounded growth through any array-shaped event field. */\nconst DEFAULT_ARRAY_MAX = 20;\n\n/** Allowlisted coding-signal bridge for domains not owned by a richer adapter. */\nexport function wireDomainEventsToChronicle(options: ChronicleDomainAdapterOptions): () => void {\n return options.events.onAny((eventName, payload) => {\n if (SPECIALIZED_RE.test(eventName)) return;\n if (!CODING_SIGNAL_RE.test(eventName)) return;\n const record = eventName === 'memory.injector_run'\n ? dedupInjectorTrace(objectPayload(payload))\n : objectPayload(payload);\n // file.event reads are already evidenced by tool.resource.observed edges;\n // only mutations need the durable session/task/board lineage record.\n if (eventName === 'file.event' && record.operation === 'read') return;\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const sessionId = stringField(record, 'sessionId');\n const agentId = stringField(record, 'agentId') ?? stringField(record, 'subagentId');\n const taskId = stringField(record, 'taskId');\n const kanbanBoardId = stringField(record, 'kanbanBoardId') ?? stringField(record, 'boardId');\n const input: ChronicleEventInput = {\n eventType: eventName,\n occurredAt: eventTime(record),\n scope: {\n ...context.scope,\n ...(sessionId ? { sessionId } : {}),\n ...(agentId ? { agentId } : {}),\n ...(taskId ? { taskId } : {}),\n ...(kanbanBoardId ? { kanbanBoardId } : {}),\n },\n correlation: {\n ...context.correlation,\n ...(stringField(record, 'traceId') ? { traceId: stringField(record, 'traceId')! } : {}),\n ...(stringField(record, 'toolCallId') ? { toolCallId: stringField(record, 'toolCallId') } : {}),\n ...(stringField(record, 'attemptId') ? { attemptId: stringField(record, 'attemptId') } : {}),\n ...(stringField(record, 'logicalRequestId') ? { logicalRequestId: stringField(record, 'logicalRequestId') } : {}),\n },\n outcome: inferOutcome(eventName, record),\n runtime: {\n ...(stringField(record, 'providerId') ?? stringField(record, 'provider') ? { providerId: stringField(record, 'providerId') ?? stringField(record, 'provider') } : {}),\n ...(stringField(record, 'modelId') ?? stringField(record, 'model') ? { modelId: stringField(record, 'modelId') ?? stringField(record, 'model') } : {}),\n },\n resource: inferResource(record, eventName),\n attributes: sanitize(record) as Record<string, unknown>,\n tags: { collector: 'eventbus-domain', family: eventName.split('.')[0] ?? 'unknown' },\n };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n });\n}\n\nfunction objectPayload(value: unknown): Record<string, unknown> {\n return value && typeof value === 'object' ? value as Record<string, unknown> : { value };\n}\n/** Persisted-copy-only dedup: an `injected` memory already present in\n * `activated` is replaced with an id reference instead of its full\n * (byte-identical) metadata. Never mutates `record`/its arrays \u2014 the same\n * payload reference is also handed to other live EventBus subscribers\n * (packages/tui/src/memory-context-monitor.ts, the WebUI memory injector\n * store) that read full fields off `injected` and must see them intact. */\nfunction dedupInjectorTrace(record: Record<string, unknown>): Record<string, unknown> {\n const activated = Array.isArray(record.activated) ? record.activated : [];\n const injected = Array.isArray(record.injected) ? record.injected : [];\n const activatedIds = new Set(\n activated\n .map((item) => (item && typeof item === 'object' ? (item as { id?: unknown }).id : undefined))\n .filter((id): id is string => typeof id === 'string'),\n );\n return {\n ...record,\n injected: injected.map((item) => {\n const id = item && typeof item === 'object' ? (item as { id?: unknown }).id : undefined;\n return typeof id === 'string' && activatedIds.has(id) ? { id, ref: 'activated' } : item;\n }),\n };\n}\nfunction stringField(value: Record<string, unknown>, key: string): string | undefined {\n return typeof value[key] === 'string' ? value[key] as string : undefined;\n}\nfunction eventTime(value: Record<string, unknown>): string | undefined {\n const raw = value.at ?? value.ts ?? value.timestamp;\n if (typeof raw === 'number' && Number.isFinite(raw)) return new Date(raw).toISOString();\n if (typeof raw === 'string' && Number.isFinite(Date.parse(raw))) return new Date(raw).toISOString();\n return undefined;\n}\nfunction inferOutcome(name: string, payload: Record<string, unknown>): ChronicleOutcome {\n if (payload.ok === false || /(?:failed|error|damaged|conflict|deadlock|denied|rejected|blocked)$/.test(name)) return 'failure';\n if (/(?:started|starting|retrying|threshold_reached)$/.test(name)) return 'started';\n if (/(?:cancelled|aborted)$/.test(name)) return 'cancelled';\n if (/(?:completed|finished|committed|merged|written|persisted|accepted|recovered|verified|connected|success)$/.test(name) || payload.ok === true) return 'success';\n return 'unknown';\n}\nfunction inferResource(payload: Record<string, unknown>, eventName?: string): ChronicleResourceRef | undefined {\n // file.event's resource IS the file \u2014 its taskId/boardId are scope, not the\n // subject. Without this the generic candidate order would pick kind 'task'\n // and drop resource.path, breaking path-filtered lineage queries.\n if (eventName === 'file.event' && typeof payload.filePath === 'string' && payload.filePath.length > 0) {\n return { kind: 'file', id: `path:${payload.filePath}`, path: payload.filePath };\n }\n const candidates: Array<[ChronicleResourceRef['kind'], string, unknown]> = [\n ['memory', 'memoryId', payload.memoryId], ['task', 'taskId', payload.taskId],\n ['kanban', 'boardId', payload.boardId ?? payload.runId], ['artifact', 'worktreeId', payload.worktreeId ?? payload.handleId],\n ['file', 'path', payload.filePath ?? payload.path], ['other', 'agentId', payload.agentId ?? payload.subagentId],\n ['network', 'serverAddress', payload.serverAddress],\n ['other', 'sessionId', payload.sessionId],\n ];\n const found = candidates.find(([, , value]) => typeof value === 'string' && value.length > 0);\n if (!found) return undefined;\n const [kind, label, value] = found as [ChronicleResourceRef['kind'], string, string];\n return { kind, id: `${label}:${value}`, ...(kind === 'file' ? { path: value } : {}) };\n}\n\nfunction sanitize(value: unknown, key = '', depth = 0, seen = new WeakSet<object>()): unknown {\n if (value === null || typeof value === 'boolean' || typeof value === 'number') return value;\n if (typeof value === 'bigint') return value.toString();\n if (typeof value === 'function') return { type: 'function' };\n if (typeof value === 'string') {\n if (PRESERVE_STRING_KEY.test(key) && !SENSITIVE_KEY.test(key)) return value.slice(0, 512);\n if (SENSITIVE_KEY.test(key)) return { hash: digest(value), length: value.length, redacted: true };\n return value.length <= 256 ? value : { hash: digest(value), length: value.length, truncated: true };\n }\n if (typeof value !== 'object') return String(value);\n if (seen.has(value)) return { circular: true };\n if (depth >= 5) return { hash: digest(safeString(value)), depthLimited: true };\n seen.add(value);\n if (Array.isArray(value)) {\n const cap = TRUNCATED_ARRAYS.has(key) ? TRUNCATED_ARRAY_MAX : DEFAULT_ARRAY_MAX;\n const items = value.slice(0, cap).map((item) => sanitize(item, key, depth + 1, seen));\n return value.length > cap ? { items, total: value.length, truncated: true } : items;\n }\n const output: Record<string, unknown> = {};\n const entries = Object.entries(value as Record<string, unknown>);\n for (const [childKey, child] of entries.slice(0, 100)) {\n if (childKey === 'ctx' || childKey === 'provider' || childKey === 'resolve' || childKey === 'extend' || childKey === 'deny') continue;\n output[childKey] = sanitize(child, childKey, depth + 1, seen);\n }\n if (entries.length > 100) output._truncatedKeys = entries.length - 100;\n return output;\n}\nfunction safeString(value: unknown): string { try { return JSON.stringify(value) ?? String(value); } catch { return String(value); } }\nfunction digest(value: string): string { return createHash('sha256').update(value).digest('hex'); }\n", "import { createHash, type Hash } from 'node:crypto';\nimport type { EventBus } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleStreamAdapterOptions {\n events: EventBus; journal: ChronicleEventSink; context: ChronicleContext | (() => ChronicleContext);\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\ninterface StreamState {\n sessionId?: string; agentId?: string; attemptId: string; logicalRequestId: string; providerId: string; model: string;\n startedAtMs: number; firstChunkAtMs?: number; lastChunkAtMs?: number;\n textChunks: number; textBytes: number; thinkingChunks: number; thinkingBytes: number;\n textHash: Hash; thinkingHash: Hash;\n}\n\n/** Max age in ms before an incomplete stream state is force-flushed as a failure. */\nconst MAX_STATE_AGE_MS = 300_000;\n\n/**\n * How often the independent stale-state reaper sweeps the states Map.\n * Set to 1/6 of MAX_STATE_AGE_MS so every stale entry is caught within\n * ~50 s of expiry regardless of whether any text delta arrives.\n */\nconst STALE_STATE_SWEEP_INTERVAL_MS = Math.round(MAX_STATE_AGE_MS / 6);\n\n/** Aggregates high-frequency streaming deltas without dropping their volume/timing/content identity. */\nexport function wireProviderStreamsToChronicle(options: ChronicleStreamAdapterOptions): () => void {\n const states = new Map<string, StreamState>();\n const key = (sessionId: string | undefined, agentId: string | undefined) => `${sessionId ?? '__default__'}\\0${agentId ?? '__leader__'}`;\n const update = (sessionId: string | undefined, agentId: string | undefined, text: string, thinking: boolean): void => {\n const now = Date.now();\n // Proactive sweep: flush every state that has been alive too long without\n // completion/failure. Runs on every delta to catch completely silent stale\n // states \u2014 even entries that never receive another delta for their own key\n // will eventually be swept when a delta arrives for ANY active attempt.\n sweepStaleStates(states, flush, now);\n const k = key(sessionId, agentId);\n const state = states.get(k);\n if (!state) return;\n const bytes = Buffer.byteLength(text);\n state.firstChunkAtMs ??= now; state.lastChunkAtMs = now;\n if (thinking) { state.thinkingChunks++; state.thinkingBytes += bytes; state.thinkingHash.update(text); }\n else { state.textChunks++; state.textBytes += bytes; state.textHash.update(text); }\n };\n const flush = (sessionId: string | undefined, agentId: string | undefined, outcome: 'success' | 'failure'): void => {\n const state = states.get(key(sessionId, agentId)); if (!state) return; states.delete(key(sessionId, agentId));\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const endedAtMs = Date.now();\n const input: ChronicleEventInput = { eventType: 'provider.stream.summarized', outcome,\n scope: { ...context.scope, ...(state.sessionId ? { sessionId: state.sessionId } : {}), ...(state.agentId ? { agentId: state.agentId } : {}) },\n correlation: { ...context.correlation, attemptId: state.attemptId, logicalRequestId: state.logicalRequestId },\n runtime: { providerId: state.providerId, modelId: state.model },\n durationNs: String(Math.max(0, endedAtMs - state.startedAtMs) * 1_000_000),\n attributes: { textChunks: state.textChunks, textBytes: state.textBytes,\n thinkingChunks: state.thinkingChunks, thinkingBytes: state.thinkingBytes,\n textHash: state.textHash.digest('hex'), thinkingHash: state.thinkingHash.digest('hex'),\n firstChunkLatencyMs: state.firstChunkAtMs === undefined ? undefined : state.firstChunkAtMs - state.startedAtMs,\n streamActiveMs: state.firstChunkAtMs === undefined || state.lastChunkAtMs === undefined ? 0 : state.lastChunkAtMs - state.firstChunkAtMs },\n };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n };\n const offs = [\n options.events.on('provider.attempt.started', (event) => states.set(key(event.sessionId,event.agentId), {\n sessionId: event.sessionId, ...(event.agentId ? { agentId:event.agentId } : {}), attemptId: event.attemptId, logicalRequestId: event.logicalRequestId,\n providerId: event.providerId, model: event.model, startedAtMs: Date.parse(event.startedAt),\n textChunks: 0, textBytes: 0, thinkingChunks: 0, thinkingBytes: 0,\n textHash: createHash('sha256'), thinkingHash: createHash('sha256'),\n })),\n options.events.on('provider.text_delta', (event) => update(event.sessionId, event.ctx.agentId, event.text, false)),\n options.events.on('provider.thinking_delta', (event) => update(event.sessionId, event.ctx.agentId, event.text, true)),\n options.events.on('provider.attempt.completed', (event) => flush(event.sessionId, event.agentId, 'success')),\n options.events.on('provider.attempt.failed', (event) => flush(event.sessionId, event.agentId, 'failure')),\n ];\n\n // Independent stale-state reaper: catches orphaned StreamState entries\n // that never receive a completion/failure event AND never see another\n // text/thinking delta (the delta-triggered sweep in update() alone is\n // not sufficient \u2014 an attempt that starts and goes silent stays in the\n // map until a DIFFERENT attempt produces a delta for a different key).\n const reaperTimer = setInterval(\n () => sweepStaleStates(states, flush, Date.now()),\n STALE_STATE_SWEEP_INTERVAL_MS,\n );\n if (typeof reaperTimer.unref === 'function') reaperTimer.unref();\n\n return () => {\n clearInterval(reaperTimer);\n for (const state of [...states.values()]) flush(state.sessionId, state.agentId, 'failure');\n offs.forEach((off) => { off(); });\n };\n}\n\n/**\n * Sweep stale states from the map \u2014 any entry past MAX_STATE_AGE_MS is\n * force-flushed as a failure and removed. Idempotent: safe to call from\n * both the delta-triggered path and the independent interval reaper.\n */\nfunction sweepStaleStates(\n states: Map<string, StreamState>,\n flushFn: (sessionId: string | undefined, agentId: string | undefined, outcome: 'success' | 'failure') => void,\n now: number,\n): void {\n if (states.size === 0) return;\n for (const s of states.values()) {\n if (now - s.startedAtMs > MAX_STATE_AGE_MS) {\n const sid = s.sessionId;\n const aid = s.agentId;\n flushFn(sid, aid, 'failure');\n }\n }\n}\n", "import { createHash } from 'node:crypto';\nimport type { ContentBlock } from '../types/blocks.js';\nimport type { Message } from '../types/messages.js';\nimport type { Request } from '../types/provider.js';\n\nexport interface ChroniclePromptManifest {\n manifestId: string;\n messageCount: number; estimatedMessageTokens: number; contentBytes: number;\n roleCounts: Record<string, number>; blockCounts: Record<string, number>;\n system: { blockCount: number; bytes: number; hash: string };\n messages: Array<{ index: number; role: string; bytes: number; estimatedTokens?: number; hash: string; blocks: Record<string, number> }>;\n tools: { count: number; estimatedDefinitionTokens: number; manifestHash: string; names: string[]; mutating: number; destructive: number };\n request: Record<string, unknown>;\n}\n\n/** Content-addressed prompt composition manifest; raw prompt/tool prose never leaves this function. */\nexport function createChroniclePromptManifest(request: Request): ChroniclePromptManifest {\n const roleCounts: Record<string, number> = {}, blockCounts: Record<string, number> = {};\n const messages = request.messages.map((message, index) => messageSummary(message, index, roleCounts, blockCounts));\n const systemText = (request.system ?? []).map((block) => block.text).join('\\n');\n const toolRecords = (request.tools ?? []).map((tool) => ({ name: tool.name, schemaHash: hash(stable(tool.inputSchema)),\n permission: tool.permission, mutating: tool.mutating, riskTier: tool.riskTier, capabilities: tool.capabilities,\n estimatedTokens: tool._estDefTokens ?? 0 }));\n const core = { systemHash: hash(systemText), messages: messages.map(({ hash: contentHash, ...rest }) => ({ ...rest, contentHash })), tools: toolRecords,\n model: request.model, maxTokens: request.maxTokens, temperature: request.temperature, topP: request.topP,\n topK: request.topK, seed: request.seed, toolChoice: request.toolChoice, reasoning: request.reasoning,\n cache: request.cache, responseFormat: request.responseFormat?.type };\n return {\n manifestId: `prompt_${hash(stable(core))}`,\n messageCount: messages.length,\n estimatedMessageTokens: messages.reduce((sum, message) => sum + (message.estimatedTokens ?? 0), 0),\n contentBytes: messages.reduce((sum, message) => sum + message.bytes, 0) + Buffer.byteLength(systemText),\n roleCounts, blockCounts,\n system: { blockCount: request.system?.length ?? 0, bytes: Buffer.byteLength(systemText), hash: hash(systemText) },\n messages,\n tools: { count: toolRecords.length, estimatedDefinitionTokens: toolRecords.reduce((sum, tool) => sum + tool.estimatedTokens, 0),\n manifestHash: hash(stable(toolRecords)), names: toolRecords.map((tool) => tool.name),\n mutating: toolRecords.filter((tool) => tool.mutating).length,\n destructive: toolRecords.filter((tool) => tool.riskTier === 'destructive').length },\n request: { maxTokens: request.maxTokens, temperature: request.temperature, topP: request.topP, topK: request.topK,\n frequencyPenalty: request.frequencyPenalty, presencePenalty: request.presencePenalty, seed: request.seed,\n candidateCount: request.candidateCount, logprobs: request.logprobs, topLogprobs: request.topLogprobs,\n stopSequenceCount: request.stopSequences?.length ?? 0, toolChoice: request.toolChoice,\n reasoning: request.reasoning, cache: request.cache, responseFormat: request.responseFormat?.type,\n safetySettingCount: request.safetySettings?.length ?? 0, userHash: request.user ? hash(request.user) : undefined },\n };\n}\n\nfunction messageSummary(message: Message, index: number, roles: Record<string, number>, totals: Record<string, number>) {\n roles[message.role] = (roles[message.role] ?? 0) + 1;\n const blocks = typeof message.content === 'string' ? { text: 1 } : countBlocks(message.content);\n for (const [type, count] of Object.entries(blocks)) totals[type] = (totals[type] ?? 0) + count;\n const content = contentIdentity(message.content);\n return { index, role: message.role, bytes: content.bytes,\n ...(message._estTokens !== undefined ? { estimatedTokens: message._estTokens } : {}), hash: content.hash, blocks };\n}\nfunction countBlocks(blocks: ContentBlock[]): Record<string, number> {\n const counts: Record<string, number> = {};\n for (const block of blocks) counts[block.type] = (counts[block.type] ?? 0) + 1;\n return counts;\n}\nfunction hash(value: string): string { return createHash('sha256').update(value).digest('hex'); }\nfunction contentIdentity(content: Message['content']): { hash: string; bytes: number } {\n if (typeof content === 'string') return { hash: hash(content), bytes: Buffer.byteLength(content) };\n const digest = createHash('sha256'); let bytes = 0;\n const add = (value: string | undefined) => { if (!value) return; digest.update(value); bytes += Buffer.byteLength(value); };\n for (const block of content) {\n add(block.type);\n if (block.type === 'text') add(block.text);\n else if (block.type === 'thinking') { add(block.thinking); add(block.signature); }\n else if (block.type === 'tool_use') { add(block.id); add(block.name); add(stable(block.input)); }\n else if (block.type === 'tool_result') { add(block.tool_use_id); add(block.name); add(block.content); add(String(block.is_error ?? false)); }\n else if (block.type === 'image') { add(block.source.type); add(block.source.media_type); add(block.source.url); add(block.source.data); }\n }\n return { hash: digest.digest('hex'), bytes };\n}\nfunction stable(value: unknown): string {\n if (value === undefined) return 'undefined';\n if (value === null || typeof value !== 'object') return JSON.stringify(value);\n if (Array.isArray(value)) return `[${value.map(stable).join(',')}]`;\n return `{${Object.entries(value as Record<string, unknown>).sort(([a], [b]) => a.localeCompare(b)).map(([key, child]) => `${JSON.stringify(key)}:${stable(child)}`).join(',')}}`;\n}\n", "import { createHash, randomUUID } from 'node:crypto';\nimport type { ChimeraReviewCompletePayload } from '../plugins/review-types.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleReviewAdapterOptions {\n events: {\n onPattern(\n pattern: string,\n handler: (event: unknown, payload: unknown) => void,\n ): () => void;\n };\n journal: ChronicleEventSink;\n context: ChronicleContext | (() => ChronicleContext);\n onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\n\n/**\n * Bridges Chimera review completions into Chronicle as structured,\n * queryable events. Each finding (severity + file:line + title) becomes\n * one Chronicle event so queries like \"which sessions had critical auth\n * findings\" are a single WHERE clause instead of a cross-store join.\n *\n * Also persists one summary event per review with duration, model, and\n * severity-count aggregates so review-level analytics (frequency, model\n * usage, cascade depth) are self-contained in Chronicle.\n */\nexport function wireReviewFindingsToChronicle(\n options: ChronicleReviewAdapterOptions,\n): () => void {\n const unsubscribe = options.events.onPattern(\n 'chimera.review_complete',\n (_event: unknown, raw: unknown) => {\n const payload = raw as ChimeraReviewCompletePayload;\n if (!payload?.reviewText) return;\n if (payload.status !== 'success') return;\n\n const context =\n typeof options.context === 'function'\n ? options.context()\n : options.context;\n const sessionId =\n payload.sessionId ?? payload.bundle?.cwd;\n const agentId =\n payload.bundle?.fileProvenance?.find((e) => e.agentId)?.agentId;\n const taskId = payload.bundle?.kanbanCard?.id;\n const provider = payload.bundle?.config?.provider;\n const model = payload.bundle?.config?.model;\n const cascadeDepth = payload.bundle?.cascadeDepth ?? 0;\n const now = new Date().toISOString();\n\n // Parse structured findings from the review text.\n // We use a minimal inline parse rather than importing\n // parseChimeraReviewReport to keep the adapter dependency-free\n // and avoid importing review-finding-parser types into chronicle.\n const findings = parseFindings(payload.reviewText);\n\n // One Chronicle event per finding\n for (const finding of findings) {\n const eventId = randomUUID();\n const input: ChronicleEventInput = {\n eventType: `finding.${finding.severity}` as const,\n occurredAt: now,\n scope: {\n ...context.scope,\n ...(sessionId ? { sessionId } : {}),\n ...(agentId ? { agentId } : {}),\n ...(taskId ? { taskId } : {}),\n },\n correlation: context.correlation,\n resource: finding.file\n ? {\n kind: 'file',\n id: `finding:${finding.fingerprint}`,\n path: finding.file,\n ...(finding.line !== undefined\n ? { lineStart: finding.line }\n : {}),\n }\n : undefined,\n outcome: 'success',\n attributes: {\n findingId: eventId,\n fingerprint: finding.fingerprint,\n severity: finding.severity,\n title: finding.title,\n file: finding.file,\n line: finding.line,\n source: 'chimera',\n model,\n provider,\n cascadeDepth,\n },\n tags: {\n collector: 'review-adapter',\n family: 'finding',\n severity: finding.severity,\n },\n };\n options.journal\n .append(input)\n .catch((error) => options.onPersistError?.(error, input));\n }\n\n // No findings \u2192 no summary either\n if (findings.length === 0) return;\n\n // Summary event per review\n const summaryInput: ChronicleEventInput = {\n eventType: 'review.completed',\n occurredAt: now,\n scope: {\n ...context.scope,\n ...(sessionId ? { sessionId } : {}),\n ...(agentId ? { agentId } : {}),\n ...(taskId ? { taskId } : {}),\n },\n correlation: context.correlation,\n outcome: 'success',\n attributes: {\n totalFindings: findings.length,\n severityCounts: aggregateSeverities(findings),\n files: payload.bundle?.files?.map((f) => f.path),\n model,\n provider,\n cascadeDepth,\n status: payload.status,\n },\n tags: {\n collector: 'review-adapter',\n family: 'review',\n },\n };\n options.journal\n .append(summaryInput)\n .catch((error) => options.onPersistError?.(error, summaryInput));\n },\n );\n\n return unsubscribe;\n}\n\n// \u2500\u2500 Minimal finding parser \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\ninterface ParsedFinding {\n severity: string;\n file?: string | undefined;\n line?: number | undefined;\n title: string;\n fingerprint: string;\n}\n\n/** Match a severity heading: ### Critical (N) */\nconst SEVERITY_HEADING = /^###\\s+(critical|high|medium|low)\\b/i;\n\n/** Match a numbered finding item: captures everything after \"N. \" */\nconst ITEM_CAPTURE = /^\\d+\\.\\s+(.*)$/;\n\n/** Match an optional [TAG] prefix at the start of content. */\nconst TAG_PREFIX = /^\\[(\\w+)\\]\\s*/;\n\n/**\n * Extract file:line \u2014 description from finding content.\n * Mirrors canonical parseFindingSegment() in review-finding-parser.ts\n * but uses `\\s+` instead of `\\s*` before the separator to prevent\n * hyphens inside file paths (e.g. `my-file.ts`) from being consumed\n * as the description separator.\n */\nconst FILE_REF = /^(.+?)(?::(\\d+))?\\s+[\u2014\u2013]\\s*(.+)$/;\n\n/** Match a path-like reference as fallback when no file:line \u2014 pattern is found. */\nconst PATH_REF = /^([a-zA-Z_./\\\\][a-zA-Z0-9_./\\\\-]*\\.\\w+)(?::(\\d+))?/;\n\nfunction parseFindings(reviewText: string): ParsedFinding[] {\n const findings: ParsedFinding[] = [];\n let currentSeverity: string | null = null;\n\n for (const rawLine of reviewText.split('\\n')) {\n const line = rawLine.trim();\n if (!line) continue;\n\n const heading = line.match(SEVERITY_HEADING);\n if (heading) {\n currentSeverity = heading[1]!.toLowerCase();\n continue;\n }\n\n if (!currentSeverity) continue;\n\n // Step 1: capture everything after \"N. \" (mirrors canonical first step)\n const item = line.match(ITEM_CAPTURE);\n if (!item) continue;\n let remaining = item[1]!.trim();\n if (!remaining) continue;\n\n // Step 2: strip optional [TAG] prefix (mirrors canonical tag extraction)\n const tag = remaining.match(TAG_PREFIX);\n if (tag) remaining = remaining.slice(tag[0].length).trim();\n\n // Step 3: extract file:line \u2014 description (mirrors canonical FILE_REF)\n const refMatch = remaining.match(FILE_REF);\n let file: string | undefined;\n let lineNum: number | undefined;\n let desc: string;\n\n if (refMatch) {\n file = refMatch[1]!.trim();\n lineNum = refMatch[2] !== undefined ? Number.parseInt(refMatch[2]!, 10) : undefined;\n desc = refMatch[3]!.trim();\n } else {\n // Step 4: fallback \u2014 try PATH_REF when no \u2014 separator (mirrors canonical fallback)\n const pathFallback = remaining.match(PATH_REF);\n if (pathFallback) {\n file = pathFallback[1]!.trim();\n lineNum = pathFallback[2] !== undefined ? Number.parseInt(pathFallback[2]!, 10) : undefined;\n const afterFile = remaining.slice(pathFallback[0].length).trim();\n desc = afterFile.replace(/^[\u2014\u2013-]\\s*/, '').trim() || remaining;\n } else {\n // No file reference at all \u2014 treat entire remaining as description\n desc = remaining;\n }\n }\n\n // Validate extracted file looks like a path; reset if not\n if (file && !file.includes('/') && !file.includes('\\\\') && !file.includes('.')) {\n file = undefined;\n desc = remaining;\n }\n\n const title = desc.split(/\\.\\s/)[0]!.trim() || desc;\n const fingerprint = computeFingerprint(file ?? '', lineNum ?? null, title);\n\n findings.push({\n severity: currentSeverity,\n file,\n line: lineNum,\n title,\n fingerprint,\n });\n }\n\n return findings;\n}\n\nfunction computeFingerprint(\n file: string,\n line: number | null,\n title: string,\n): string {\n const normalizedFile = file.replace(/\\\\/g, '/').trim().toLowerCase();\n const lineStr = line != null && line >= 0 ? String(line) : '0';\n const normalizedTitle = title\n .trim()\n .toLowerCase()\n .replace(/[^\\w\\s]/g, '')\n .replace(/\\s+/g, ' ')\n .trim();\n const hash = createHash('sha256');\n hash.update(`${normalizedFile}:${lineStr}:${normalizedTitle}`);\n return hash.digest('hex');\n}\n\nfunction aggregateSeverities(\n findings: ParsedFinding[],\n): Record<string, number> {\n const counts: Record<string, number> = {\n critical: 0,\n high: 0,\n medium: 0,\n low: 0,\n };\n for (const f of findings) {\n const sev = f.severity;\n if (sev in counts) counts[sev]!++;\n }\n return counts;\n}\n", "import { createHash } from 'node:crypto';\nimport type { EventBus } from '../kernel/events.js';\nimport type { ChronicleContext } from './context.js';\nimport type { ChronicleEventSink } from './sink.js';\nimport type { ChronicleEventInput } from './types.js';\n\nexport interface ChronicleRollupAdapterOptions {\n events: EventBus; journal: ChronicleEventSink; context: ChronicleContext | (() => ChronicleContext);\n windowMs?: number; onPersistError?: ((error: unknown, event: ChronicleEventInput) => void) | undefined;\n}\ninterface Bucket { signal: string; sessionId?: string; agentId?: string; toolCallId?: string;\n dimensions: Record<string, string>; startedAt: number; updatedAt: number; count: number;\n metrics: Record<string, { sum: number; min: number; max: number; last: number }>;\n categories: Record<string, number>; digest: ReturnType<typeof createHash>;\n /** Distinct resources touched (tool.resource rollups only) \u2014 id-keyed so kind/path survive. */\n resources: Map<string, { kind: string; path?: string }> }\n\nconst MAX_ROLLUP_RESOURCES = 100;\n\n/** Converts high-frequency ephemeral signals into bounded window aggregates before persistence. */\nexport function wireRollupsToChronicle(options: ChronicleRollupAdapterOptions): () => void {\n const buckets = new Map<string, Bucket>(); const windowMs = Math.max(1_000, options.windowMs ?? 10_000);\n const bucket = (key: string, seed: Omit<Bucket, 'startedAt'|'updatedAt'|'count'|'metrics'|'categories'|'digest'|'resources'>) => {\n let value = buckets.get(key); if (!value) { const now = Date.now(); value = { ...seed, startedAt: now, updatedAt: now,\n count: 0, metrics: {}, categories: {}, digest: createHash('sha256'), resources: new Map() }; buckets.set(key, value); } return value;\n };\n const sample = (target: Bucket, values: Record<string, number>, category?: string, digest?: string) => {\n target.count++; target.updatedAt = Date.now();\n for (const [name, value] of Object.entries(values)) { const metric = target.metrics[name];\n target.metrics[name] = metric ? { sum: metric.sum + value, min: Math.min(metric.min, value), max: Math.max(metric.max, value), last: value }\n : { sum: value, min: value, max: value, last: value }; }\n if (category) target.categories[category] = (target.categories[category] ?? 0) + 1;\n if (digest) target.digest.update(digest);\n };\n const flush = (key: string) => { const value = buckets.get(key); if (!value || value.count === 0) return; buckets.delete(key);\n const context = typeof options.context === 'function' ? options.context() : options.context;\n const stats = Object.fromEntries(Object.entries(value.metrics).map(([name, metric]) => [name, { ...metric, avg: metric.sum / value.count }]));\n const resources = value.resources.size > 0\n ? [...value.resources].slice(0, MAX_ROLLUP_RESOURCES).map(([id, r]) => ({ id, kind: r.kind, ...(r.path ? { path: r.path } : {}) }))\n : undefined;\n const input: ChronicleEventInput = { eventType: 'metrics.rollup', outcome: 'success', occurredAt: new Date(value.updatedAt).toISOString(),\n scope: { ...context.scope, ...(value.sessionId ? { sessionId: value.sessionId } : {}), ...(value.agentId ? { agentId: value.agentId } : {}) },\n correlation: { ...context.correlation, ...(value.toolCallId ? { toolCallId: value.toolCallId } : {}) },\n durationNs: String(Math.max(0, value.updatedAt - value.startedAt) * 1_000_000),\n attributes: { signal: value.signal, windowStart: new Date(value.startedAt).toISOString(), windowEnd: new Date(value.updatedAt).toISOString(),\n samples: value.count, dimensions: value.dimensions, stats, categories: value.categories, digest: value.digest.digest('hex'), rawEventsRetained: false,\n ...(resources ? { resources, resourceCount: value.resources.size } : {}) } };\n void options.journal.append(input).catch((error) => options.onPersistError?.(error, input));\n };\n const gauge = (signal: string, event: Record<string, unknown>, dimension?: string) => { const sessionId = text(event.sessionId);\n const dimensionValue = dimension ? text(event[dimension]) : undefined; const key = `${signal}\\0${sessionId ?? ''}\\0${dimensionValue ?? ''}`;\n const target = bucket(key, { signal, ...(sessionId ? { sessionId } : {}), ...(dimensionValue ? { agentId: dimensionValue } : {}), dimensions: dimensionValue && dimension ? { [dimension]: dimensionValue } : {} });\n sample(target, Object.fromEntries(Object.entries(event).filter(([, value]) => typeof value === 'number')) as Record<string, number>); };\n const offs = [\n options.events.on('process.output', (event) => { const key = `process.output\\0${event.sessionId}\\0${event.toolCallId}\\0${event.pid ?? ''}\\0${event.stream}`;\n const target = bucket(key, { signal: 'process.output', sessionId: event.sessionId, ...(event.agentId ? { agentId: event.agentId } : {}), toolCallId: event.toolCallId,\n dimensions: { stream: event.stream, toolName: event.toolName, pid: String(event.pid ?? '') } }); sample(target, { bytes: event.bytes }, event.stream, event.chunkHash); }),\n options.events.on('process.completed', (event) => { for (const key of [...buckets.keys()]) if (key.startsWith(`process.output\\0${event.sessionId}\\0${event.toolCallId}\\0`)) flush(key); }),\n options.events.on('tool.progress', (event) => { if (event.event.type === 'file_changed') return; const key = `tool.progress\\0${event.sessionId ?? ''}\\0${event.id}`;\n const target = bucket(key, { signal: 'tool.progress', ...(event.sessionId ? { sessionId: event.sessionId } : {}), ...(event.agentId ? { agentId: event.agentId } : {}), toolCallId: event.id, dimensions: { toolName: event.name } });\n sample(target, { textBytes: Buffer.byteLength(event.event.text ?? '') }, event.event.type, safeDigest(event.event)); }),\n options.events.on('tool.executed', (event) => {\n flush(`tool.progress\\0${event.sessionId ?? ''}\\0${event.id ?? ''}`);\n // Resources a leader-level tool call touched (files read/grepped,\n // symbols, commands) \u2014 one bounded rollup per call instead of one raw\n // tool.resource.observed event per resource. Subagent calls never\n // carry this metadata (see host-event-bridge.ts), so nothing here.\n const metadata = event.metadata;\n if (!metadata || (metadata.files.length === 0 && metadata.symbols.length === 0 && metadata.commands.length === 0)) return;\n const key = `tool.resource\\0${event.sessionId ?? ''}\\0${event.id ?? ''}`;\n const target = bucket(key, { signal: 'tool.resource.observed',\n ...(event.sessionId ? { sessionId: event.sessionId } : {}), ...(event.agentId ? { agentId: event.agentId } : {}),\n ...(event.id ? { toolCallId: event.id } : {}), dimensions: { toolName: event.name } });\n for (const file of metadata.files) { target.resources.set(resourceId('file', file), { kind: 'file', path: file }); sample(target, {}, 'file'); }\n for (const symbol of metadata.symbols) { target.resources.set(resourceId('symbol', symbol), { kind: 'symbol' }); sample(target, {}, 'symbol'); }\n for (const command of metadata.commands) { target.resources.set(resourceId('command', command), { kind: 'process' }); sample(target, {}, 'command'); }\n flush(key);\n }),\n options.events.on('tool.failed', (event) => flush(`tool.progress\\0${event.sessionId}\\0${event.id}`)),\n options.events.on('ctx.pct', (event) => gauge('ctx.pct', event)),\n options.events.on('subagent.ctx_pct', (event) => gauge('subagent.ctx_pct', event, 'subagentId')),\n options.events.on('countdown.tick', (event) => gauge('countdown.tick', event)),\n options.events.on('coordinator.stats', (event) => gauge('coordinator.stats', event)),\n // Periodic self-observation gauge (nested fields, so the flat gauge()\n // helper can't be reused directly \u2014 flatten before sampling).\n options.events.on('runtime.health.sampled', (event) => {\n const key = `runtime.health\\0${event.sessionId ?? ''}`;\n const target = bucket(key, { signal: 'runtime.health', ...(event.sessionId ? { sessionId: event.sessionId } : {}), dimensions: {} });\n const chronicle = event.chronicle as { pendingEvents?: unknown; rejectedEvents?: unknown } | undefined;\n sample(target, {\n 'eventLoop.utilization': event.eventLoop.utilization,\n 'eventLoop.delayMeanMs': event.eventLoop.delayMeanMs,\n 'eventLoop.delayP95Ms': event.eventLoop.delayP95Ms,\n 'eventLoop.delayMaxMs': event.eventLoop.delayMaxMs,\n 'cpu.userMicros': event.cpu.userMicros,\n 'cpu.systemMicros': event.cpu.systemMicros,\n 'memory.rssBytes': event.memory.rssBytes,\n 'memory.heapUsedBytes': event.memory.heapUsedBytes,\n 'memory.heapTotalBytes': event.memory.heapTotalBytes,\n ...(typeof chronicle?.pendingEvents === 'number' ? { 'chronicle.pendingEvents': chronicle.pendingEvents } : {}),\n ...(typeof chronicle?.rejectedEvents === 'number' ? { 'chronicle.rejectedEvents': chronicle.rejectedEvents } : {}),\n });\n }),\n // Full-fleet snapshots fired on every agent-state flush (~14KB each) are\n // reduced to one windowed aggregate per session; the raw event is excluded\n // from the domain adapter. Sums preserve the fleet-level metric trail.\n options.events.on('session.agents_updated', (event) => {\n const key = `session.agents\\0${event.sessionId ?? ''}`;\n const target = bucket(key, { signal: 'session.agents', ...(event.sessionId ? { sessionId: event.sessionId } : {}), dimensions: {} });\n const sums = { agents: 0, running: 0, iterations: 0, toolCalls: 0, costUsd: 0, tokensIn: 0, tokensOut: 0 };\n for (const agent of event.agents) {\n sums.agents++;\n if (agent.status === 'running') sums.running++;\n sums.iterations += numeric(agent.iterations); sums.toolCalls += numeric(agent.toolCalls);\n sums.costUsd += numeric(agent.costUsd); sums.tokensIn += numeric(agent.tokensIn); sums.tokensOut += numeric(agent.tokensOut);\n }\n sample(target, sums);\n }),\n // Per-request network chatter (started/completed pairs were the 2nd most\n // frequent raw family) becomes one aggregate per session\u00D7initiator\u00D7host\n // window with status-class categories. network.request.failed stays raw.\n options.events.on('network.request.completed', (event) => {\n const key = `network.request\\0${event.sessionId}\\0${event.initiator}\\0${event.serverAddress}`;\n const target = bucket(key, { signal: 'network.request', sessionId: event.sessionId,\n dimensions: { initiator: event.initiator, serverAddress: event.serverAddress } });\n sample(target, {\n durationMs: event.durationMs,\n ...(event.requestBytes !== undefined ? { requestBytes: event.requestBytes } : {}),\n ...(event.responseBytes !== undefined ? { responseBytes: event.responseBytes } : {}),\n }, `${Math.floor(event.statusCode / 100)}xx`, event.requestId);\n }),\n ];\n const timer = setInterval(() => { const cutoff = Date.now() - windowMs; for (const [key, value] of buckets) if (value.updatedAt <= cutoff) flush(key); }, windowMs);\n timer.unref?.();\n return () => { clearInterval(timer); for (const key of [...buckets.keys()]) flush(key); offs.forEach((off) => { off(); }); };\n}\nfunction text(value: unknown): string | undefined { return typeof value === 'string' ? value : undefined; }\nfunction numeric(value: unknown): number { return typeof value === 'number' && Number.isFinite(value) ? value : 0; }\nfunction safeDigest(value: unknown): string { try { return createHash('sha256').update(JSON.stringify(value)).digest('hex'); } catch { return 'unhashable'; } }\n/** Matches tool-adapter.ts's scheme exactly so a resource observed here and\n * one mutated via file.mutation.observed resolve to the same graph node. */\nfunction resourceId(kind: string, value: string): string {\n return `${kind}_${createHash('sha256').update(value).digest('hex').slice(0, 24)}`;\n}\n"],
|
|
5
|
-
"mappings": "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",
|
|
6
|
-
"names": ["createHash", "path", "path", "relative", "stat", "createHash", "os", "path", "createHash", "fs", "os", "path", "hash", "projectHash", "randomUUID", "fs", "path", "createHash", "path", "randomUUID", "resolve", "hash", "text", "stat", "fs", "path", "createHash", "createReadStream", "fs", "path", "createInterface", "fs", "path", "createReadStream", "createInterface", "trimmed", "normalize", "createHash", "stableStringify", "durationMs", "readPath", "numberAt", "scopeKey", "fs", "path", "randomUUID", "createRequire", "path", "encodeCursor", "decodeCursor", "SCHEMA_VERSION", "Ctor", "loadDatabaseSync", "createRequire", "randomUUID", "hash", "fs", "path", "createHash", "os", "path", "createHash", "resolve", "journal", "durationMs", "createHash", "persist", "millisecondsToNanoseconds", "resourceId", "durationMs", "createHash", "persist", "performance", "delay", "createHash", "createHash", "value", "createHash", "text", "createHash", "hash", "digest", "createHash", "randomUUID", "fingerprint", "hash", "createHash", "digest", "resourceId"]
|
|
7
|
-
}
|