devchain-cli 0.17.1 → 0.18.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/README.md +64 -96
- package/dist/drizzle/0067_remove_claude_1m_provider_state.sql +3 -0
- package/dist/drizzle/0068_claude_launch_settings_json.sql +1 -0
- package/dist/drizzle/meta/0067_snapshot.json +5743 -0
- package/dist/drizzle/meta/0068_snapshot.json +5750 -0
- package/dist/drizzle/meta/_journal.json +15 -1
- package/dist/node_modules/@devchain/codebase-overview/tsconfig.tsbuildinfo +1 -1
- package/dist/node_modules/@devchain/shared/index.d.ts +1 -1
- package/dist/node_modules/@devchain/shared/index.d.ts.map +1 -1
- package/dist/node_modules/@devchain/shared/index.js +1 -1
- package/dist/node_modules/@devchain/shared/index.js.map +1 -1
- package/dist/node_modules/@devchain/shared/schemas/claude-launch-settings.d.ts +12 -0
- package/dist/node_modules/@devchain/shared/schemas/claude-launch-settings.d.ts.map +1 -0
- package/dist/node_modules/@devchain/shared/schemas/claude-launch-settings.js +97 -0
- package/dist/node_modules/@devchain/shared/schemas/claude-launch-settings.js.map +1 -0
- package/dist/node_modules/@devchain/shared/schemas/export-schema.d.ts +18 -10
- package/dist/node_modules/@devchain/shared/schemas/export-schema.d.ts.map +1 -1
- package/dist/node_modules/@devchain/shared/schemas/export-schema.js +11 -2
- package/dist/node_modules/@devchain/shared/schemas/export-schema.js.map +1 -1
- package/dist/node_modules/@devchain/shared/schemas/index.d.ts +1 -0
- package/dist/node_modules/@devchain/shared/schemas/index.d.ts.map +1 -1
- package/dist/node_modules/@devchain/shared/schemas/index.js +1 -0
- package/dist/node_modules/@devchain/shared/schemas/index.js.map +1 -1
- package/dist/node_modules/@devchain/shared/session-migration-reasons.d.ts +20 -0
- package/dist/node_modules/@devchain/shared/session-migration-reasons.d.ts.map +1 -0
- package/dist/node_modules/@devchain/shared/session-migration-reasons.js +109 -0
- package/dist/node_modules/@devchain/shared/session-migration-reasons.js.map +1 -0
- package/dist/node_modules/@devchain/shared/tsconfig.tsbuildinfo +1 -1
- package/dist/server/app.main.module.js +2 -0
- package/dist/server/app.main.module.js.map +1 -1
- package/dist/server/app.normal.module.js +2 -0
- package/dist/server/app.normal.module.js.map +1 -1
- package/dist/server/common/prompt-references.d.ts +29 -0
- package/dist/server/common/prompt-references.js +84 -0
- package/dist/server/common/prompt-references.js.map +1 -0
- package/dist/server/common/prompt-transfer.d.ts +31 -0
- package/dist/server/common/prompt-transfer.js +38 -0
- package/dist/server/common/prompt-transfer.js.map +1 -0
- package/dist/server/common/prompt-type.d.ts +12 -0
- package/dist/server/common/prompt-type.js +46 -0
- package/dist/server/common/prompt-type.js.map +1 -0
- package/dist/server/common/tags.d.ts +7 -0
- package/dist/server/common/tags.js +21 -0
- package/dist/server/common/tags.js.map +1 -0
- package/dist/server/main.js +9 -1
- package/dist/server/main.js.map +1 -1
- package/dist/server/modules/cloud-tunnel/services/mobile-chat-rpc.service.d.ts +9 -0
- package/dist/server/modules/cloud-tunnel/services/mobile-chat-rpc.service.js +33 -0
- package/dist/server/modules/cloud-tunnel/services/mobile-chat-rpc.service.js.map +1 -1
- package/dist/server/modules/cloud-tunnel/services/tunnel-handler.service.js +15 -0
- package/dist/server/modules/cloud-tunnel/services/tunnel-handler.service.js.map +1 -1
- package/dist/server/modules/core/services/preflight.service.js +28 -4
- package/dist/server/modules/core/services/preflight.service.js.map +1 -1
- package/dist/server/modules/events/catalog/broadcast-registry.js +29 -12
- package/dist/server/modules/events/catalog/broadcast-registry.js.map +1 -1
- package/dist/server/modules/events/catalog/index.d.ts +30 -3
- package/dist/server/modules/events/catalog/index.js +2 -0
- package/dist/server/modules/events/catalog/index.js.map +1 -1
- package/dist/server/modules/events/catalog/session.runtime-context.updated.d.ts +12 -0
- package/dist/server/modules/events/catalog/session.runtime-context.updated.js +13 -0
- package/dist/server/modules/events/catalog/session.runtime-context.updated.js.map +1 -0
- package/dist/server/modules/events/catalog/session.transcript.updated.d.ts +23 -3
- package/dist/server/modules/events/catalog/session.transcript.updated.js +41 -19
- package/dist/server/modules/events/catalog/session.transcript.updated.js.map +1 -1
- package/dist/server/modules/hooks/dtos/hook-event.dto.d.ts +50 -0
- package/dist/server/modules/hooks/dtos/hook-event.dto.js +18 -1
- package/dist/server/modules/hooks/dtos/hook-event.dto.js.map +1 -1
- package/dist/server/modules/hooks/hooks.module.js +2 -1
- package/dist/server/modules/hooks/hooks.module.js.map +1 -1
- package/dist/server/modules/hooks/services/hooks.service.d.ts +4 -1
- package/dist/server/modules/hooks/services/hooks.service.js +15 -3
- package/dist/server/modules/hooks/services/hooks.service.js.map +1 -1
- package/dist/server/modules/mcp/dtos/mcp.dto.d.ts +24 -0
- package/dist/server/modules/mcp/dtos/mcp.dto.js.map +1 -1
- package/dist/server/modules/mcp/services/handlers/agent-context.d.ts +2 -2
- package/dist/server/modules/mcp/services/handlers/agent-tools.js +103 -16
- package/dist/server/modules/mcp/services/handlers/agent-tools.js.map +1 -1
- package/dist/server/modules/mcp/services/handlers/prompt-tools.js +11 -9
- package/dist/server/modules/mcp/services/handlers/prompt-tools.js.map +1 -1
- package/dist/server/modules/mcp/services/instructions-resolver.js +14 -10
- package/dist/server/modules/mcp/services/instructions-resolver.js.map +1 -1
- package/dist/server/modules/mcp/tool-descriptors/agent.metadata.js +1 -1
- package/dist/server/modules/mcp/tool-descriptors/agent.metadata.js.map +1 -1
- package/dist/server/modules/metrics/controllers/metrics.controller.d.ts +6 -0
- package/dist/server/modules/metrics/controllers/metrics.controller.js +38 -0
- package/dist/server/modules/metrics/controllers/metrics.controller.js.map +1 -0
- package/dist/server/modules/metrics/helpers/byte-accounting.helper.d.ts +17 -0
- package/dist/server/modules/metrics/helpers/byte-accounting.helper.js +88 -0
- package/dist/server/modules/metrics/helpers/byte-accounting.helper.js.map +1 -0
- package/dist/server/modules/metrics/metrics.module.d.ts +2 -0
- package/dist/server/modules/metrics/metrics.module.js +23 -0
- package/dist/server/modules/metrics/metrics.module.js.map +1 -0
- package/dist/server/modules/metrics/services/metrics.service.d.ts +20 -0
- package/dist/server/modules/metrics/services/metrics.service.js +241 -0
- package/dist/server/modules/metrics/services/metrics.service.js.map +1 -0
- package/dist/server/modules/metrics/types/metrics.types.d.ts +100 -0
- package/dist/server/modules/{providers/adapters/capabilities/context-window.capability.js → metrics/types/metrics.types.js} +1 -1
- package/dist/server/modules/metrics/types/metrics.types.js.map +1 -0
- package/dist/server/modules/profiles/dto.d.ts +2 -2
- package/dist/server/modules/profiles/dto.js +14 -2
- package/dist/server/modules/profiles/dto.js.map +1 -1
- package/dist/server/modules/projects/controllers/projects.controller.d.ts +5 -6
- package/dist/server/modules/projects/helpers/profile-mapping.helpers.d.ts +5 -3
- package/dist/server/modules/projects/helpers/profile-mapping.helpers.js +25 -13
- package/dist/server/modules/projects/helpers/profile-mapping.helpers.js.map +1 -1
- package/dist/server/modules/projects/helpers/project-export.d.ts +0 -2
- package/dist/server/modules/projects/helpers/project-export.js +7 -3
- package/dist/server/modules/projects/helpers/project-export.js.map +1 -1
- package/dist/server/modules/projects/helpers/project-import.d.ts +7 -6
- package/dist/server/modules/projects/helpers/project-import.js +66 -105
- package/dist/server/modules/projects/helpers/project-import.js.map +1 -1
- package/dist/server/modules/projects/helpers/project-runtime.helpers.d.ts +1 -0
- package/dist/server/modules/projects/helpers/project-runtime.helpers.js +2 -1
- package/dist/server/modules/projects/helpers/project-runtime.helpers.js.map +1 -1
- package/dist/server/modules/projects/helpers/template-loader.d.ts +3 -3
- package/dist/server/modules/projects/helpers/template-loader.js +32 -12
- package/dist/server/modules/projects/helpers/template-loader.js.map +1 -1
- package/dist/server/modules/projects/projects.module.js +0 -2
- package/dist/server/modules/projects/projects.module.js.map +1 -1
- package/dist/server/modules/projects/services/project-registry-import.service.d.ts +2 -0
- package/dist/server/modules/projects/services/project-registry-import.service.js +29 -1
- package/dist/server/modules/projects/services/project-registry-import.service.js.map +1 -1
- package/dist/server/modules/projects/services/project-template-upgrade.service.d.ts +5 -0
- package/dist/server/modules/projects/services/project-template-upgrade.service.js +22 -2
- package/dist/server/modules/projects/services/project-template-upgrade.service.js.map +1 -1
- package/dist/server/modules/projects/services/projects.service.d.ts +12 -20
- package/dist/server/modules/projects/services/projects.service.js +8 -9
- package/dist/server/modules/projects/services/projects.service.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codec-registry.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/agents.codec.d.ts +1 -1
- package/dist/server/modules/projects/template-codec/codecs/agents.codec.js +4 -4
- package/dist/server/modules/projects/template-codec/codecs/agents.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/profiles.codec.d.ts +1 -1
- package/dist/server/modules/projects/template-codec/codecs/profiles.codec.js +27 -8
- package/dist/server/modules/projects/template-codec/codecs/profiles.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/project-settings.codec.js +8 -1
- package/dist/server/modules/projects/template-codec/codecs/project-settings.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/prompts.codec.js +23 -4
- package/dist/server/modules/projects/template-codec/codecs/prompts.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/provider-settings.codec.d.ts +0 -5
- package/dist/server/modules/projects/template-codec/codecs/provider-settings.codec.js +10 -46
- package/dist/server/modules/projects/template-codec/codecs/provider-settings.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/codecs/watchers.codec.js +1 -1
- package/dist/server/modules/projects/template-codec/codecs/watchers.codec.js.map +1 -1
- package/dist/server/modules/projects/template-codec/import-context.d.ts +6 -1
- package/dist/server/modules/projects/template-codec/import-context.js.map +1 -1
- package/dist/server/modules/projects/template-codec/template-section-codec.d.ts +7 -5
- package/dist/server/modules/providers/adapters/capabilities/auto-compact.capability.d.ts +13 -0
- package/dist/server/modules/providers/adapters/capabilities/auto-compact.capability.js +3 -0
- package/dist/server/modules/providers/adapters/capabilities/auto-compact.capability.js.map +1 -0
- package/dist/server/modules/providers/adapters/capabilities/index.d.ts +2 -2
- package/dist/server/modules/providers/adapters/capabilities/index.js +2 -2
- package/dist/server/modules/providers/adapters/capabilities/index.js.map +1 -1
- package/dist/server/modules/providers/adapters/capabilities/type-guards.d.ts +3 -3
- package/dist/server/modules/providers/adapters/capabilities/type-guards.js +3 -3
- package/dist/server/modules/providers/adapters/capabilities/type-guards.js.map +1 -1
- package/dist/server/modules/providers/adapters/claude.adapter.d.ts +3 -7
- package/dist/server/modules/providers/adapters/claude.adapter.js +5 -45
- package/dist/server/modules/providers/adapters/claude.adapter.js.map +1 -1
- package/dist/server/modules/providers/controllers/providers.controller.d.ts +3 -7
- package/dist/server/modules/providers/controllers/providers.controller.js +2 -14
- package/dist/server/modules/providers/controllers/providers.controller.js.map +1 -1
- package/dist/server/modules/providers/providers.module.js +0 -2
- package/dist/server/modules/providers/providers.module.js.map +1 -1
- package/dist/server/modules/providers/services/provider-state-manager.service.d.ts +4 -10
- package/dist/server/modules/providers/services/provider-state-manager.service.js +28 -83
- package/dist/server/modules/providers/services/provider-state-manager.service.js.map +1 -1
- package/dist/server/modules/registry/controllers/templates.controller.d.ts +2 -4
- package/dist/server/modules/runtime-context-capture/claude-launch-settings-materializer.service.d.ts +32 -0
- package/dist/server/modules/runtime-context-capture/claude-launch-settings-materializer.service.js +364 -0
- package/dist/server/modules/runtime-context-capture/claude-launch-settings-materializer.service.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/context-window-policy.d.ts +40 -0
- package/dist/server/modules/runtime-context-capture/context-window-policy.js +73 -0
- package/dist/server/modules/runtime-context-capture/context-window-policy.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/index.d.ts +6 -0
- package/dist/server/modules/runtime-context-capture/index.js +23 -0
- package/dist/server/modules/runtime-context-capture/index.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture-files.d.ts +4 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture-files.js +40 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture-files.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.module.d.ts +2 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.module.js +25 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.module.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.service.d.ts +25 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.service.js +155 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.service.js.map +1 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.types.d.ts +44 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.types.js +5 -0
- package/dist/server/modules/runtime-context-capture/runtime-context-capture.types.js.map +1 -0
- package/dist/server/modules/seeders/seeders/0011_seed_remove_claude_1m_provider_env.d.ts +3 -0
- package/dist/server/modules/seeders/seeders/0011_seed_remove_claude_1m_provider_env.js +31 -0
- package/dist/server/modules/seeders/seeders/0011_seed_remove_claude_1m_provider_env.js.map +1 -0
- package/dist/server/modules/seeders/seeders/0012_seed_claude_launch_settings.d.ts +3 -0
- package/dist/server/modules/seeders/seeders/0012_seed_claude_launch_settings.js +28 -0
- package/dist/server/modules/seeders/seeders/0012_seed_claude_launch_settings.js.map +1 -0
- package/dist/server/modules/seeders/seeders/0013_seed_prompt_type_tags.d.ts +3 -0
- package/dist/server/modules/seeders/seeders/0013_seed_prompt_type_tags.js +112 -0
- package/dist/server/modules/seeders/seeders/0013_seed_prompt_type_tags.js.map +1 -0
- package/dist/server/modules/seeders/services/data-seeder.service.js +6 -0
- package/dist/server/modules/seeders/services/data-seeder.service.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/antigravity-session-reader.adapter.d.ts +6 -0
- package/dist/server/modules/session-reader/adapters/antigravity-session-reader.adapter.js +66 -0
- package/dist/server/modules/session-reader/adapters/antigravity-session-reader.adapter.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/claude-session-reader.adapter.d.ts +5 -0
- package/dist/server/modules/session-reader/adapters/claude-session-reader.adapter.js +12 -0
- package/dist/server/modules/session-reader/adapters/claude-session-reader.adapter.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/codex-session-reader.adapter.d.ts +5 -0
- package/dist/server/modules/session-reader/adapters/codex-session-reader.adapter.js +12 -0
- package/dist/server/modules/session-reader/adapters/codex-session-reader.adapter.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/copilot-session-reader.adapter.d.ts +5 -0
- package/dist/server/modules/session-reader/adapters/copilot-session-reader.adapter.js +12 -0
- package/dist/server/modules/session-reader/adapters/copilot-session-reader.adapter.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/opencode-session-reader.adapter.d.ts +5 -0
- package/dist/server/modules/session-reader/adapters/opencode-session-reader.adapter.js +15 -0
- package/dist/server/modules/session-reader/adapters/opencode-session-reader.adapter.js.map +1 -1
- package/dist/server/modules/session-reader/adapters/session-reader-adapter.interface.d.ts +10 -0
- package/dist/server/modules/session-reader/adapters/session-reader-adapter.interface.js +28 -1
- package/dist/server/modules/session-reader/adapters/session-reader-adapter.interface.js.map +1 -1
- package/dist/server/modules/session-reader/controllers/session-reader.controller.d.ts +10 -4
- package/dist/server/modules/session-reader/controllers/session-reader.controller.js +18 -19
- package/dist/server/modules/session-reader/controllers/session-reader.controller.js.map +1 -1
- package/dist/server/modules/session-reader/data/pricing.json +334 -6
- package/dist/server/modules/session-reader/parsers/claude-jsonl.parser.d.ts +1 -0
- package/dist/server/modules/session-reader/parsers/claude-jsonl.parser.js +7 -3
- package/dist/server/modules/session-reader/parsers/claude-jsonl.parser.js.map +1 -1
- package/dist/server/modules/session-reader/parsers/codex-jsonl.parser.d.ts +1 -0
- package/dist/server/modules/session-reader/parsers/codex-jsonl.parser.js +22 -11
- package/dist/server/modules/session-reader/parsers/codex-jsonl.parser.js.map +1 -1
- package/dist/server/modules/session-reader/parsers/copilot-jsonl.parser.d.ts +1 -0
- package/dist/server/modules/session-reader/parsers/copilot-jsonl.parser.js +22 -9
- package/dist/server/modules/session-reader/parsers/copilot-jsonl.parser.js.map +1 -1
- package/dist/server/modules/session-reader/readers/opencode-sqlite.reader.d.ts +5 -1
- package/dist/server/modules/session-reader/readers/opencode-sqlite.reader.js +102 -0
- package/dist/server/modules/session-reader/readers/opencode-sqlite.reader.js.map +1 -1
- package/dist/server/modules/session-reader/services/pricing.interface.d.ts +2 -0
- package/dist/server/modules/session-reader/services/pricing.interface.js +3 -0
- package/dist/server/modules/session-reader/services/pricing.interface.js.map +1 -1
- package/dist/server/modules/session-reader/services/pricing.service.d.ts +1 -0
- package/dist/server/modules/session-reader/services/pricing.service.js +4 -2
- package/dist/server/modules/session-reader/services/pricing.service.js.map +1 -1
- package/dist/server/modules/session-reader/services/session-cache.service.d.ts +72 -4
- package/dist/server/modules/session-reader/services/session-cache.service.js +435 -68
- package/dist/server/modules/session-reader/services/session-cache.service.js.map +1 -1
- package/dist/server/modules/session-reader/services/session-reader.service.d.ts +33 -9
- package/dist/server/modules/session-reader/services/session-reader.service.js +200 -79
- package/dist/server/modules/session-reader/services/session-reader.service.js.map +1 -1
- package/dist/server/modules/session-reader/services/transcript-cursor.d.ts +1 -1
- package/dist/server/modules/session-reader/services/transcript-cursor.js +2 -2
- package/dist/server/modules/session-reader/services/transcript-cursor.js.map +1 -1
- package/dist/server/modules/session-reader/services/transcript-watcher.service.d.ts +3 -0
- package/dist/server/modules/session-reader/services/transcript-watcher.service.js +66 -11
- package/dist/server/modules/session-reader/services/transcript-watcher.service.js.map +1 -1
- package/dist/server/modules/session-reader/session-reader.module.js +12 -2
- package/dist/server/modules/session-reader/session-reader.module.js.map +1 -1
- package/dist/server/modules/sessions/dtos/sessions.dto.d.ts +1 -0
- package/dist/server/modules/sessions/dtos/sessions.dto.js.map +1 -1
- package/dist/server/modules/sessions/services/agent-presence-aggregator.d.ts +1 -0
- package/dist/server/modules/sessions/services/agent-presence-aggregator.js +1 -0
- package/dist/server/modules/sessions/services/agent-presence-aggregator.js.map +1 -1
- package/dist/server/modules/sessions/services/provider-launch-config/provider-launch-config.service.d.ts +6 -2
- package/dist/server/modules/sessions/services/provider-launch-config/provider-launch-config.service.js +24 -8
- package/dist/server/modules/sessions/services/provider-launch-config/provider-launch-config.service.js.map +1 -1
- package/dist/server/modules/sessions/services/session-runtime/__test-utils__/pipeline-harness.d.ts +30 -5
- package/dist/server/modules/sessions/services/session-runtime/__test-utils__/pipeline-harness.js +51 -8
- package/dist/server/modules/sessions/services/session-runtime/__test-utils__/pipeline-harness.js.map +1 -1
- package/dist/server/modules/sessions/services/session-runtime/session-launch-pipeline.service.d.ts +5 -1
- package/dist/server/modules/sessions/services/session-runtime/session-launch-pipeline.service.js +39 -6
- package/dist/server/modules/sessions/services/session-runtime/session-launch-pipeline.service.js.map +1 -1
- package/dist/server/modules/sessions/services/session-runtime/session-restore-pipeline.service.d.ts +7 -1
- package/dist/server/modules/sessions/services/session-runtime/session-restore-pipeline.service.js +47 -5
- package/dist/server/modules/sessions/services/session-runtime/session-restore-pipeline.service.js.map +1 -1
- package/dist/server/modules/sessions/services/sessions.service.d.ts +6 -1
- package/dist/server/modules/sessions/services/sessions.service.js +17 -3
- package/dist/server/modules/sessions/services/sessions.service.js.map +1 -1
- package/dist/server/modules/sessions/sessions.module.js +2 -0
- package/dist/server/modules/sessions/sessions.module.js.map +1 -1
- package/dist/server/modules/sessions/utils/profile-options.d.ts +1 -2
- package/dist/server/modules/sessions/utils/profile-options.js +3 -50
- package/dist/server/modules/sessions/utils/profile-options.js.map +1 -1
- package/dist/server/modules/storage/db/schema.d.ts +10 -87
- package/dist/server/modules/storage/db/schema.js +3 -13
- package/dist/server/modules/storage/db/schema.js.map +1 -1
- package/dist/server/modules/storage/interfaces/snapshot-prompt-writer.interface.d.ts +5 -0
- package/dist/server/modules/storage/interfaces/snapshot-prompt-writer.interface.js +5 -0
- package/dist/server/modules/storage/interfaces/snapshot-prompt-writer.interface.js.map +1 -0
- package/dist/server/modules/storage/local/delegates/prompt.delegate.d.ts +2 -0
- package/dist/server/modules/storage/local/delegates/prompt.delegate.js +31 -20
- package/dist/server/modules/storage/local/delegates/prompt.delegate.js.map +1 -1
- package/dist/server/modules/storage/local/delegates/provider.delegate.js +61 -16
- package/dist/server/modules/storage/local/delegates/provider.delegate.js.map +1 -1
- package/dist/server/modules/storage/local/local-storage.service.d.ts +3 -1
- package/dist/server/modules/storage/local/local-storage.service.js +3 -0
- package/dist/server/modules/storage/local/local-storage.service.js.map +1 -1
- package/dist/server/modules/storage/models/domain.models.d.ts +2 -4
- package/dist/server/modules/storage/storage.module.js +8 -2
- package/dist/server/modules/storage/storage.module.js.map +1 -1
- package/dist/server/modules/terminal/dtos/ws-envelope.dto.d.ts +185 -1
- package/dist/server/modules/terminal/dtos/ws-envelope.dto.js +93 -2
- package/dist/server/modules/terminal/dtos/ws-envelope.dto.js.map +1 -1
- package/dist/server/modules/terminal/gateways/terminal.gateway.d.ts +47 -2
- package/dist/server/modules/terminal/gateways/terminal.gateway.js +615 -62
- package/dist/server/modules/terminal/gateways/terminal.gateway.js.map +1 -1
- package/dist/server/modules/terminal/services/process-executor/fake-process-executor.d.ts +1 -0
- package/dist/server/modules/terminal/services/process-executor/fake-process-executor.js +1 -0
- package/dist/server/modules/terminal/services/process-executor/fake-process-executor.js.map +1 -1
- package/dist/server/modules/terminal/services/pty.service.d.ts +8 -3
- package/dist/server/modules/terminal/services/pty.service.js +11 -2
- package/dist/server/modules/terminal/services/pty.service.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-io/capture.js +2 -0
- package/dist/server/modules/terminal/services/terminal-io/capture.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-io/delivery.d.ts +1 -0
- package/dist/server/modules/terminal/services/terminal-io/delivery.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-io/terminal-io.service.js +28 -1
- package/dist/server/modules/terminal/services/terminal-io/terminal-io.service.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-key-input/terminal-key-input.facade.d.ts +6 -0
- package/dist/server/modules/terminal/services/terminal-key-input/terminal-key-input.facade.js +26 -1
- package/dist/server/modules/terminal/services/terminal-key-input/terminal-key-input.facade.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-seed.service.d.ts +27 -3
- package/dist/server/modules/terminal/services/terminal-seed.service.js +75 -19
- package/dist/server/modules/terminal/services/terminal-seed.service.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-send-scheduler.service.d.ts +73 -0
- package/dist/server/modules/terminal/services/terminal-send-scheduler.service.js +387 -0
- package/dist/server/modules/terminal/services/terminal-send-scheduler.service.js.map +1 -0
- package/dist/server/modules/terminal/services/terminal-session/terminal-session.d.ts +4 -10
- package/dist/server/modules/terminal/services/terminal-session/terminal-session.js +20 -48
- package/dist/server/modules/terminal/services/terminal-session/terminal-session.js.map +1 -1
- package/dist/server/modules/terminal/services/terminal-socket-drain.adapter.d.ts +10 -0
- package/dist/server/modules/terminal/services/terminal-socket-drain.adapter.js +75 -0
- package/dist/server/modules/terminal/services/terminal-socket-drain.adapter.js.map +1 -0
- package/dist/server/modules/terminal/services/terminal-stream.service.d.ts +53 -6
- package/dist/server/modules/terminal/services/terminal-stream.service.js +190 -35
- package/dist/server/modules/terminal/services/terminal-stream.service.js.map +1 -1
- package/dist/server/modules/terminal/terminal.module.js +7 -0
- package/dist/server/modules/terminal/terminal.module.js.map +1 -1
- package/dist/server/templates/3-agents-dev.json +120 -105
- package/dist/server/templates/teams-dev.json +204 -180
- package/dist/server/tsconfig.tsbuildinfo +1 -1
- package/dist/server/ui/assets/{ReviewDetailPage-DdJqgIFY.js → ReviewDetailPage-CkB_Fx1C.js} +1 -1
- package/dist/server/ui/assets/{ReviewsPage-iWEVgAdp.js → ReviewsPage-Bx6-dM75.js} +1 -1
- package/dist/server/ui/assets/index-5SDRTmwU.js +1156 -0
- package/dist/server/ui/assets/index-PyQSKUPl.css +32 -0
- package/dist/server/ui/assets/{useReviewSubscription-DCXbfBtE.js → useReviewSubscription-BZxAz2ZG.js} +1 -1
- package/dist/server/ui/index.html +2 -2
- package/dist/templates/3-agents-dev.json +120 -105
- package/dist/templates/teams-dev.json +204 -180
- package/package.json +20 -5
- package/dist/server/modules/providers/adapters/capabilities/context-window.capability.d.ts +0 -20
- package/dist/server/modules/providers/adapters/capabilities/context-window.capability.js.map +0 -1
- package/dist/server/modules/providers/services/probe-proof.service.d.ts +0 -8
- package/dist/server/modules/providers/services/probe-proof.service.js +0 -49
- package/dist/server/modules/providers/services/probe-proof.service.js.map +0 -1
- package/dist/server/modules/providers/utils/probe-1m.d.ts +0 -8
- package/dist/server/modules/providers/utils/probe-1m.js +0 -76
- package/dist/server/modules/providers/utils/probe-1m.js.map +0 -1
- package/dist/server/ui/assets/index-CM2KuqcE.js +0 -1113
- package/dist/server/ui/assets/index-COvyD_66.css +0 -32
|
@@ -38,76 +38,228 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
38
38
|
return result;
|
|
39
39
|
};
|
|
40
40
|
})();
|
|
41
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
42
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
43
|
+
};
|
|
44
|
+
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
45
|
+
return function (target, key) { decorator(target, key, paramIndex); }
|
|
46
|
+
};
|
|
41
47
|
var SessionCacheService_1;
|
|
42
48
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
43
|
-
exports.SessionCacheService = void 0;
|
|
49
|
+
exports.SessionCacheService = exports.TRANSCRIPT_CACHE_CONFIG = void 0;
|
|
50
|
+
exports.getTranscriptCacheConfig = getTranscriptCacheConfig;
|
|
44
51
|
const common_1 = require("@nestjs/common");
|
|
52
|
+
const node_crypto_1 = require("node:crypto");
|
|
45
53
|
const fs = __importStar(require("node:fs/promises"));
|
|
46
54
|
const estimate_content_tokens_1 = require("../adapters/utils/estimate-content-tokens");
|
|
47
55
|
const tool_result_fold_1 = require("../adapters/utils/tool-result-fold");
|
|
48
56
|
const coalesce_turns_1 = require("../adapters/utils/coalesce-turns");
|
|
49
|
-
const
|
|
50
|
-
const
|
|
57
|
+
const metrics_service_1 = require("../../metrics/services/metrics.service");
|
|
58
|
+
const DEFAULT_CACHE_IDLE_TTL_MS = 10 * 60 * 1_000;
|
|
59
|
+
const DEFAULT_CACHE_SWEEP_INTERVAL_MS = 60_000;
|
|
60
|
+
const DEFAULT_CACHE_BUDGET_BYTES = 64 * 1024 * 1024;
|
|
61
|
+
const SAFE_INTEGER_LOW_BITS = 0x20_0000;
|
|
62
|
+
const FILE_HASH_CHUNK_BYTES = 64 * 1024;
|
|
63
|
+
function fileSourceVersion(stat) {
|
|
64
|
+
const digest = (0, node_crypto_1.createHash)('sha256')
|
|
65
|
+
.update(`${stat.dev}:${stat.ino}:${stat.size}:${stat.mtimeMs}`)
|
|
66
|
+
.digest();
|
|
67
|
+
return digest.readUInt32BE(0) * SAFE_INTEGER_LOW_BITS + (digest.readUInt32BE(4) >>> 11);
|
|
68
|
+
}
|
|
69
|
+
exports.TRANSCRIPT_CACHE_CONFIG = Symbol('TRANSCRIPT_CACHE_CONFIG');
|
|
70
|
+
function getTranscriptCacheConfig() {
|
|
71
|
+
return {
|
|
72
|
+
budgetBytes: positiveIntegerFromEnv(process.env.TRANSCRIPT_CACHE_MAX_BYTES, DEFAULT_CACHE_BUDGET_BYTES),
|
|
73
|
+
idleTtlMs: positiveIntegerFromEnv(process.env.TRANSCRIPT_CACHE_IDLE_TTL_MS, DEFAULT_CACHE_IDLE_TTL_MS),
|
|
74
|
+
sweepIntervalMs: positiveIntegerFromEnv(process.env.TRANSCRIPT_CACHE_SWEEP_INTERVAL_MS, DEFAULT_CACHE_SWEEP_INTERVAL_MS),
|
|
75
|
+
};
|
|
76
|
+
}
|
|
51
77
|
let SessionCacheService = SessionCacheService_1 = class SessionCacheService {
|
|
52
|
-
constructor() {
|
|
78
|
+
constructor(metricsService, config) {
|
|
79
|
+
this.metricsService = metricsService;
|
|
53
80
|
this.logger = new common_1.Logger(SessionCacheService_1.name);
|
|
54
81
|
this.cache = new Map();
|
|
82
|
+
this.hits = 0;
|
|
83
|
+
this.misses = 0;
|
|
84
|
+
this.chunksHits = 0;
|
|
85
|
+
this.chunksMisses = 0;
|
|
86
|
+
this.dtoHits = 0;
|
|
87
|
+
this.dtoMisses = 0;
|
|
88
|
+
this.budgetUsedBytes = 0;
|
|
89
|
+
this.evictions = 0;
|
|
90
|
+
this.config = config ?? getTranscriptCacheConfig();
|
|
91
|
+
}
|
|
92
|
+
onModuleInit() {
|
|
93
|
+
this.metricsService.registerCacheStatsProvider('parsed', () => this.getCacheStats(), () => Array.from(this.cache.values(), (entry) => entry.session));
|
|
94
|
+
this.metricsService.registerCacheStatsProvider('chunks', () => this.getChunksCacheStats(), () => this.getChunksRetainedRoots());
|
|
95
|
+
this.idleSweepTimer = setInterval(() => this.sweepIdleEntries(), this.config.sweepIntervalMs);
|
|
96
|
+
this.idleSweepTimer.unref();
|
|
55
97
|
}
|
|
56
98
|
onModuleDestroy() {
|
|
57
|
-
this.
|
|
99
|
+
if (this.idleSweepTimer) {
|
|
100
|
+
clearInterval(this.idleSweepTimer);
|
|
101
|
+
this.idleSweepTimer = undefined;
|
|
102
|
+
}
|
|
103
|
+
this.clear();
|
|
104
|
+
}
|
|
105
|
+
getCacheStats() {
|
|
106
|
+
const total = this.hits + this.misses;
|
|
107
|
+
return {
|
|
108
|
+
entries: this.cache.size,
|
|
109
|
+
bytesEstimated: 0,
|
|
110
|
+
hits: this.hits,
|
|
111
|
+
misses: this.misses,
|
|
112
|
+
hitRate: total > 0 ? this.hits / total : 0,
|
|
113
|
+
bytesMethod: 'deferred-to-aggregate',
|
|
114
|
+
budgetUsedBytes: this.budgetUsedBytes,
|
|
115
|
+
budgetBytes: this.config.budgetBytes,
|
|
116
|
+
evictions: this.evictions,
|
|
117
|
+
};
|
|
118
|
+
}
|
|
119
|
+
getChunksCacheStats() {
|
|
120
|
+
const total = this.chunksHits + this.chunksMisses;
|
|
121
|
+
let entries = 0;
|
|
122
|
+
for (const entry of this.cache.values()) {
|
|
123
|
+
if (entry.chunks)
|
|
124
|
+
entries += 1;
|
|
125
|
+
}
|
|
126
|
+
return {
|
|
127
|
+
entries,
|
|
128
|
+
bytesEstimated: 0,
|
|
129
|
+
hits: this.chunksHits,
|
|
130
|
+
misses: this.chunksMisses,
|
|
131
|
+
hitRate: total > 0 ? this.chunksHits / total : 0,
|
|
132
|
+
bytesMethod: 'deferred-to-aggregate',
|
|
133
|
+
};
|
|
134
|
+
}
|
|
135
|
+
getDtoCacheStats() {
|
|
136
|
+
let entries = 0;
|
|
137
|
+
let bytesEstimated = 0;
|
|
138
|
+
for (const entry of this.cache.values()) {
|
|
139
|
+
if (!entry.dto)
|
|
140
|
+
continue;
|
|
141
|
+
entries += 1;
|
|
142
|
+
bytesEstimated += entry.dto.responseBytes;
|
|
143
|
+
}
|
|
144
|
+
const total = this.dtoHits + this.dtoMisses;
|
|
145
|
+
return {
|
|
146
|
+
entries,
|
|
147
|
+
bytesEstimated,
|
|
148
|
+
hits: this.dtoHits,
|
|
149
|
+
misses: this.dtoMisses,
|
|
150
|
+
hitRate: total > 0 ? this.dtoHits / total : 0,
|
|
151
|
+
bytesMethod: 'json-stringify-length',
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
async getFreshSession(sessionId, source, adapter) {
|
|
155
|
+
const cached = this.cache.get(sessionId);
|
|
156
|
+
if (!cached)
|
|
157
|
+
return undefined;
|
|
158
|
+
const ref = this.toSourceRef(source, adapter);
|
|
159
|
+
const freshness = await this.computeFreshness(ref, adapter);
|
|
160
|
+
return this.takeFreshCachedSession(sessionId, cached, freshness.token, Date.now());
|
|
58
161
|
}
|
|
59
162
|
async getOrParse(sessionId, source, adapter) {
|
|
163
|
+
return (await this.getOrParseResult(sessionId, source, adapter)).session;
|
|
164
|
+
}
|
|
165
|
+
async getOrParseWithMeta(sessionId, source, adapter) {
|
|
166
|
+
return this.getOrParseResult(sessionId, source, adapter);
|
|
167
|
+
}
|
|
168
|
+
async getOrParseResult(sessionId, source, adapter) {
|
|
60
169
|
const now = Date.now();
|
|
61
170
|
const ref = this.toSourceRef(source, adapter);
|
|
62
171
|
const threadRef = typeof source !== 'string' ? ref : undefined;
|
|
63
|
-
|
|
172
|
+
let freshness = await this.computeFreshness(ref, adapter);
|
|
64
173
|
const cached = this.cache.get(sessionId);
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
this.logger.debug({ sessionId }, 'Session cache hit');
|
|
69
|
-
this.touchLru(sessionId, cached);
|
|
70
|
-
return cached.session;
|
|
174
|
+
const freshSession = this.takeFreshCachedSession(sessionId, cached, freshness.token, now);
|
|
175
|
+
if (freshSession && cached) {
|
|
176
|
+
return this.toGetOrParseResult(freshSession, cached, true, 'cache-hit');
|
|
71
177
|
}
|
|
178
|
+
this.misses += 1;
|
|
72
179
|
let session;
|
|
73
180
|
let lastOffset;
|
|
74
181
|
let boundaryFold = false;
|
|
75
|
-
|
|
182
|
+
let acceptedFileDigests;
|
|
183
|
+
const sameFileIdentity = ref.kind !== 'file' ||
|
|
184
|
+
(cached?.fileIdentity !== undefined && cached.fileIdentity === freshness.fileIdentity);
|
|
185
|
+
const fileReplaced = cached !== undefined && ref.kind === 'file' && !sameFileIdentity;
|
|
186
|
+
const sameIdentityGrowth = cached !== undefined &&
|
|
187
|
+
ref.kind === 'file' &&
|
|
188
|
+
sameFileIdentity &&
|
|
189
|
+
freshness.size > cached.lastSize;
|
|
190
|
+
const growthDigests = sameIdentityGrowth && cached.fileContentDigest !== undefined
|
|
191
|
+
? await this.tryHashFileContent(ref.filePath, freshness, cached.lastOffset)
|
|
192
|
+
: undefined;
|
|
193
|
+
const provenSameFileAppend = sameIdentityGrowth &&
|
|
194
|
+
cached.fileContentDigest !== undefined &&
|
|
195
|
+
growthDigests?.prefixDigest === cached.fileContentDigest;
|
|
196
|
+
let sourceChangeKind = !cached
|
|
197
|
+
? 'unknown-full-parse'
|
|
198
|
+
: ref.kind === 'db'
|
|
199
|
+
? 'db-update'
|
|
200
|
+
: fileReplaced
|
|
201
|
+
? 'file-replacement'
|
|
202
|
+
: freshness.size > cached.lastSize
|
|
203
|
+
? provenSameFileAppend
|
|
204
|
+
? 'same-file-append'
|
|
205
|
+
: 'same-file-rewrite'
|
|
206
|
+
: freshness.size < cached.lastSize
|
|
207
|
+
? 'file-truncation'
|
|
208
|
+
: 'same-file-rewrite';
|
|
209
|
+
if (cached && provenSameFileAppend && growthDigests) {
|
|
76
210
|
this.logger.debug({ sessionId, lastOffset: cached.lastOffset, currentSize: freshness.size }, 'Incremental parse (source grew)');
|
|
77
211
|
const incOptions = { byteOffset: cached.lastOffset, includeToolCalls: true };
|
|
78
|
-
|
|
212
|
+
let tentativeResult = threadRef
|
|
79
213
|
? await adapter.parseIncremental(ref.filePath, incOptions, threadRef)
|
|
80
214
|
: await adapter.parseIncremental(ref.filePath, incOptions);
|
|
81
|
-
const
|
|
82
|
-
if (
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
215
|
+
const postParseDigests = await this.tryHashFileContent(ref.filePath, freshness, freshness.size);
|
|
216
|
+
if (postParseDigests?.fullDigest !== growthDigests.fullDigest) {
|
|
217
|
+
this.logger.debug({ sessionId }, 'Discarding incremental parse because its proven file revision drifted');
|
|
218
|
+
tentativeResult = undefined;
|
|
219
|
+
freshness = await this.computeFreshness(ref, adapter);
|
|
220
|
+
sourceChangeKind = this.classifyUnsafeFileChange(cached, freshness);
|
|
221
|
+
session = threadRef
|
|
222
|
+
? await adapter.parseFullSession(ref.filePath, threadRef)
|
|
223
|
+
: await adapter.parseFullSession(ref.filePath);
|
|
224
|
+
lastOffset = freshness.size;
|
|
91
225
|
}
|
|
92
226
|
else {
|
|
93
|
-
const
|
|
94
|
-
|
|
95
|
-
const
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
}
|
|
227
|
+
const acceptedResult = tentativeResult;
|
|
228
|
+
acceptedFileDigests = postParseDigests;
|
|
229
|
+
const newMessages = acceptedResult.entries;
|
|
230
|
+
if (adapter.incrementalMode === 'snapshot') {
|
|
231
|
+
const snapshotMetrics = acceptedResult.metrics ?? cached.session.metrics;
|
|
232
|
+
session = {
|
|
233
|
+
...cached.session,
|
|
234
|
+
messages: newMessages,
|
|
235
|
+
metrics: snapshotMetrics,
|
|
236
|
+
isOngoing: snapshotMetrics.isOngoing,
|
|
237
|
+
warnings: this.mergeWarnings(cached.session.warnings, acceptedResult.warnings),
|
|
238
|
+
};
|
|
239
|
+
}
|
|
240
|
+
else {
|
|
241
|
+
const folded = this.foldLeadingContinuationIntoCachedTail(cached.session.messages, newMessages);
|
|
242
|
+
boundaryFold = folded.tailMutatedWithoutNewMessage;
|
|
243
|
+
const mergedMessages = folded.merged;
|
|
244
|
+
const mergedMetrics = acceptedResult.metrics
|
|
245
|
+
? this.mergeMetrics(cached.session.metrics, acceptedResult.metrics, mergedMessages)
|
|
246
|
+
: cached.session.metrics;
|
|
247
|
+
session = {
|
|
248
|
+
...cached.session,
|
|
249
|
+
messages: mergedMessages,
|
|
250
|
+
metrics: mergedMetrics,
|
|
251
|
+
isOngoing: mergedMetrics.isOngoing,
|
|
252
|
+
warnings: this.mergeWarnings(cached.session.warnings, acceptedResult.warnings),
|
|
253
|
+
};
|
|
254
|
+
}
|
|
255
|
+
lastOffset = acceptedResult.nextByteOffset;
|
|
106
256
|
}
|
|
107
|
-
lastOffset = result.nextByteOffset;
|
|
108
257
|
}
|
|
109
258
|
else {
|
|
110
|
-
if (
|
|
259
|
+
if (fileReplaced) {
|
|
260
|
+
this.logger.debug({ sessionId }, 'Full reparse (source replaced)');
|
|
261
|
+
}
|
|
262
|
+
else if (cached && freshness.size < cached.lastSize) {
|
|
111
263
|
this.logger.debug({ sessionId }, 'Full reparse (source truncated)');
|
|
112
264
|
}
|
|
113
265
|
session = threadRef
|
|
@@ -119,58 +271,183 @@ let SessionCacheService = SessionCacheService_1 = class SessionCacheService {
|
|
|
119
271
|
if (coalesced.messages !== session.messages) {
|
|
120
272
|
session = { ...session, messages: coalesced.messages, metrics: coalesced.metrics };
|
|
121
273
|
}
|
|
122
|
-
this.
|
|
123
|
-
|
|
124
|
-
|
|
274
|
+
session = this.withoutDerivedChunks(session);
|
|
275
|
+
const fileContentDigest = ref.kind === 'file'
|
|
276
|
+
? lastOffset === freshness.size && acceptedFileDigests !== undefined
|
|
277
|
+
? acceptedFileDigests.fullDigest
|
|
278
|
+
: (await this.tryHashFileContent(ref.filePath, freshness, lastOffset))?.prefixDigest
|
|
279
|
+
: undefined;
|
|
280
|
+
this.deleteEntry(sessionId);
|
|
281
|
+
const sourceWeightBytes = this.estimateSourceWeight(ref, session, freshness.size);
|
|
282
|
+
const entry = {
|
|
125
283
|
session,
|
|
126
284
|
lastOffset,
|
|
127
285
|
lastSize: freshness.size,
|
|
128
286
|
lastMtime: freshness.mtimeMs,
|
|
287
|
+
fileIdentity: freshness.fileIdentity,
|
|
288
|
+
fileContentDigest,
|
|
129
289
|
sourceVersion: freshness.sourceVersion,
|
|
130
290
|
freshnessToken: freshness.token,
|
|
131
|
-
|
|
291
|
+
lastAccessedAt: now,
|
|
292
|
+
sourceWeightBytes,
|
|
293
|
+
weights: { parsed: sourceWeightBytes * 2, chunks: 0, dto: 0 },
|
|
132
294
|
boundaryFold,
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
const prevSession = this.cache.get(sessionId)?.session;
|
|
138
|
-
const session = await this.getOrParse(sessionId, source, adapter);
|
|
139
|
-
const entry = this.cache.get(sessionId);
|
|
295
|
+
};
|
|
296
|
+
this.cache.set(sessionId, entry);
|
|
297
|
+
this.budgetUsedBytes += entry.weights.parsed;
|
|
298
|
+
this.enforceBudget();
|
|
140
299
|
return {
|
|
141
300
|
session,
|
|
142
|
-
cacheHit:
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
301
|
+
cacheHit: false,
|
|
302
|
+
sourceChangeKind,
|
|
303
|
+
lastOffset,
|
|
304
|
+
lastSize: freshness.size,
|
|
305
|
+
lastMtime: freshness.mtimeMs,
|
|
306
|
+
sourceVersion: freshness.sourceVersion,
|
|
307
|
+
boundaryFold,
|
|
148
308
|
};
|
|
149
309
|
}
|
|
150
310
|
getEntry(sessionId) {
|
|
151
311
|
return this.cache.get(sessionId);
|
|
152
312
|
}
|
|
313
|
+
getChunks(sessionId, sourceVersion) {
|
|
314
|
+
const entry = this.cache.get(sessionId);
|
|
315
|
+
if (!entry?.chunks || entry.chunks.sourceVersion !== sourceVersion) {
|
|
316
|
+
this.chunksMisses += 1;
|
|
317
|
+
return undefined;
|
|
318
|
+
}
|
|
319
|
+
this.chunksHits += 1;
|
|
320
|
+
this.touchLru(sessionId, entry, Date.now());
|
|
321
|
+
return entry.chunks.chunks;
|
|
322
|
+
}
|
|
323
|
+
setChunks(sessionId, sourceVersion, chunks) {
|
|
324
|
+
const entry = this.cache.get(sessionId);
|
|
325
|
+
if (!entry || entry.sourceVersion !== sourceVersion)
|
|
326
|
+
return;
|
|
327
|
+
this.budgetUsedBytes -= entry.weights.chunks;
|
|
328
|
+
entry.chunks = { chunks, sourceVersion };
|
|
329
|
+
entry.weights.chunks = entry.sourceWeightBytes;
|
|
330
|
+
this.budgetUsedBytes += entry.weights.chunks;
|
|
331
|
+
this.touchLru(sessionId, entry, Date.now());
|
|
332
|
+
this.enforceBudget();
|
|
333
|
+
}
|
|
334
|
+
getDto(sessionId, maxToolResultLength, enrichmentFingerprint) {
|
|
335
|
+
const entry = this.cache.get(sessionId);
|
|
336
|
+
const dto = entry?.dto;
|
|
337
|
+
if (!entry ||
|
|
338
|
+
!dto ||
|
|
339
|
+
dto.maxToolResultLength !== maxToolResultLength ||
|
|
340
|
+
dto.enrichmentFingerprint !== enrichmentFingerprint) {
|
|
341
|
+
this.dtoMisses += 1;
|
|
342
|
+
return undefined;
|
|
343
|
+
}
|
|
344
|
+
this.dtoHits += 1;
|
|
345
|
+
this.touchLru(sessionId, entry, Date.now());
|
|
346
|
+
return dto;
|
|
347
|
+
}
|
|
348
|
+
setDto(sessionId, dto) {
|
|
349
|
+
const entry = this.cache.get(sessionId);
|
|
350
|
+
if (!entry)
|
|
351
|
+
return;
|
|
352
|
+
this.budgetUsedBytes -= entry.weights.dto;
|
|
353
|
+
entry.dto = dto;
|
|
354
|
+
entry.weights.dto = dto.responseBytes;
|
|
355
|
+
this.budgetUsedBytes += entry.weights.dto;
|
|
356
|
+
this.touchLru(sessionId, entry, Date.now());
|
|
357
|
+
this.enforceBudget();
|
|
358
|
+
}
|
|
359
|
+
invalidateDto(sessionId) {
|
|
360
|
+
const entry = this.cache.get(sessionId);
|
|
361
|
+
if (!entry?.dto)
|
|
362
|
+
return;
|
|
363
|
+
this.budgetUsedBytes -= entry.weights.dto;
|
|
364
|
+
entry.dto = undefined;
|
|
365
|
+
entry.weights.dto = 0;
|
|
366
|
+
}
|
|
367
|
+
getDtoRetainedRoots() {
|
|
368
|
+
return Array.from(this.cache.values(), (entry) => entry.dto?.result);
|
|
369
|
+
}
|
|
370
|
+
getChunksRetainedRoots() {
|
|
371
|
+
return Array.from(this.cache.values(), (entry) => entry.chunks?.chunks);
|
|
372
|
+
}
|
|
373
|
+
sweepIdleEntries(now = Date.now()) {
|
|
374
|
+
let swept = 0;
|
|
375
|
+
for (const [sessionId, entry] of this.cache) {
|
|
376
|
+
if (now - entry.lastAccessedAt < this.config.idleTtlMs)
|
|
377
|
+
continue;
|
|
378
|
+
this.deleteEntry(sessionId);
|
|
379
|
+
swept += 1;
|
|
380
|
+
}
|
|
381
|
+
return swept;
|
|
382
|
+
}
|
|
153
383
|
invalidate(sessionId) {
|
|
154
|
-
this.
|
|
384
|
+
this.deleteEntry(sessionId);
|
|
155
385
|
}
|
|
156
386
|
clear() {
|
|
157
387
|
this.cache.clear();
|
|
388
|
+
this.budgetUsedBytes = 0;
|
|
158
389
|
}
|
|
159
390
|
get size() {
|
|
160
391
|
return this.cache.size;
|
|
161
392
|
}
|
|
162
|
-
|
|
393
|
+
takeFreshCachedSession(sessionId, cached, freshnessToken, now) {
|
|
394
|
+
if (!cached || JSON.stringify(cached.freshnessToken) !== JSON.stringify(freshnessToken)) {
|
|
395
|
+
return undefined;
|
|
396
|
+
}
|
|
397
|
+
this.logger.debug({ sessionId }, 'Session cache hit');
|
|
398
|
+
this.touchLru(sessionId, cached, now);
|
|
399
|
+
this.hits += 1;
|
|
400
|
+
return cached.session;
|
|
401
|
+
}
|
|
402
|
+
toGetOrParseResult(session, entry, cacheHit, sourceChangeKind) {
|
|
403
|
+
return {
|
|
404
|
+
session,
|
|
405
|
+
cacheHit,
|
|
406
|
+
sourceChangeKind,
|
|
407
|
+
lastOffset: entry.lastOffset,
|
|
408
|
+
lastSize: entry.lastSize,
|
|
409
|
+
lastMtime: entry.lastMtime,
|
|
410
|
+
sourceVersion: entry.sourceVersion,
|
|
411
|
+
boundaryFold: entry.boundaryFold,
|
|
412
|
+
};
|
|
413
|
+
}
|
|
414
|
+
touchLru(sessionId, entry, now) {
|
|
415
|
+
entry.lastAccessedAt = now;
|
|
163
416
|
this.cache.delete(sessionId);
|
|
164
417
|
this.cache.set(sessionId, entry);
|
|
165
418
|
}
|
|
166
|
-
|
|
167
|
-
|
|
419
|
+
enforceBudget() {
|
|
420
|
+
while (this.budgetUsedBytes > this.config.budgetBytes && this.cache.size > 0) {
|
|
168
421
|
const oldestKey = this.cache.keys().next().value;
|
|
169
422
|
if (oldestKey !== undefined) {
|
|
170
|
-
this.
|
|
423
|
+
this.deleteEntry(oldestKey);
|
|
424
|
+
this.evictions += 1;
|
|
171
425
|
}
|
|
172
426
|
}
|
|
173
427
|
}
|
|
428
|
+
deleteEntry(sessionId) {
|
|
429
|
+
const entry = this.cache.get(sessionId);
|
|
430
|
+
if (!entry)
|
|
431
|
+
return;
|
|
432
|
+
this.budgetUsedBytes -= this.entryWeight(entry);
|
|
433
|
+
this.cache.delete(sessionId);
|
|
434
|
+
}
|
|
435
|
+
entryWeight(entry) {
|
|
436
|
+
return entry.weights.parsed + entry.weights.chunks + entry.weights.dto;
|
|
437
|
+
}
|
|
438
|
+
estimateSourceWeight(ref, session, sourceSize) {
|
|
439
|
+
if (ref.kind === 'file')
|
|
440
|
+
return Math.max(1, sourceSize);
|
|
441
|
+
const tokenProxy = Math.max(session.metrics.totalContextConsumption, session.metrics.totalTokens, session.metrics.visibleContextTokens) * 4;
|
|
442
|
+
return Math.max(1_024, tokenProxy, session.messages.length * 256);
|
|
443
|
+
}
|
|
444
|
+
withoutDerivedChunks(session) {
|
|
445
|
+
if (session.chunks === undefined)
|
|
446
|
+
return session;
|
|
447
|
+
const parsedSession = { ...session };
|
|
448
|
+
delete parsedSession.chunks;
|
|
449
|
+
return parsedSession;
|
|
450
|
+
}
|
|
174
451
|
foldLeadingContinuationIntoCachedTail(cachedMessages, newMessages) {
|
|
175
452
|
const tail = cachedMessages[cachedMessages.length - 1];
|
|
176
453
|
if (!tail || tail.role !== 'assistant' || newMessages.length === 0) {
|
|
@@ -266,7 +543,79 @@ let SessionCacheService = SessionCacheService_1 = class SessionCacheService {
|
|
|
266
543
|
}
|
|
267
544
|
async statFile(filePath) {
|
|
268
545
|
const stat = await fs.stat(filePath);
|
|
269
|
-
return {
|
|
546
|
+
return {
|
|
547
|
+
size: stat.size,
|
|
548
|
+
mtimeMs: stat.mtime.getTime(),
|
|
549
|
+
dev: stat.dev,
|
|
550
|
+
ino: stat.ino,
|
|
551
|
+
fileIdentity: `${stat.dev}:${stat.ino}`,
|
|
552
|
+
};
|
|
553
|
+
}
|
|
554
|
+
classifyUnsafeFileChange(cached, current) {
|
|
555
|
+
if (cached.fileIdentity === undefined ||
|
|
556
|
+
current.fileIdentity === undefined ||
|
|
557
|
+
cached.fileIdentity !== current.fileIdentity) {
|
|
558
|
+
return 'file-replacement';
|
|
559
|
+
}
|
|
560
|
+
if (current.size < cached.lastSize) {
|
|
561
|
+
return 'file-truncation';
|
|
562
|
+
}
|
|
563
|
+
return 'same-file-rewrite';
|
|
564
|
+
}
|
|
565
|
+
async tryHashFileContent(filePath, expected, prefixLength) {
|
|
566
|
+
try {
|
|
567
|
+
return await this.hashFileContent(filePath, expected, prefixLength);
|
|
568
|
+
}
|
|
569
|
+
catch (error) {
|
|
570
|
+
this.logger.debug({ error, filePath }, 'File prefix proof unavailable — append is unsafe');
|
|
571
|
+
return undefined;
|
|
572
|
+
}
|
|
573
|
+
}
|
|
574
|
+
async hashFileContent(filePath, expected, prefixLength) {
|
|
575
|
+
if (!Number.isSafeInteger(prefixLength) ||
|
|
576
|
+
prefixLength < 0 ||
|
|
577
|
+
prefixLength > expected.size ||
|
|
578
|
+
expected.fileIdentity === undefined) {
|
|
579
|
+
throw new Error('Invalid file prefix proof bounds');
|
|
580
|
+
}
|
|
581
|
+
const handle = await fs.open(filePath, 'r');
|
|
582
|
+
const assertStableSnapshot = async () => {
|
|
583
|
+
const current = await handle.stat();
|
|
584
|
+
if (current.size !== expected.size ||
|
|
585
|
+
current.mtime.getTime() !== expected.mtimeMs ||
|
|
586
|
+
`${current.dev}:${current.ino}` !== expected.fileIdentity) {
|
|
587
|
+
throw new Error('File changed while computing append proof');
|
|
588
|
+
}
|
|
589
|
+
};
|
|
590
|
+
try {
|
|
591
|
+
await assertStableSnapshot();
|
|
592
|
+
const prefixHash = (0, node_crypto_1.createHash)('sha256');
|
|
593
|
+
const fullHash = (0, node_crypto_1.createHash)('sha256');
|
|
594
|
+
const buffer = Buffer.allocUnsafe(Math.min(FILE_HASH_CHUNK_BYTES, Math.max(1, expected.size)));
|
|
595
|
+
let position = 0;
|
|
596
|
+
while (position < expected.size) {
|
|
597
|
+
const requested = Math.min(buffer.byteLength, expected.size - position);
|
|
598
|
+
const { bytesRead } = await handle.read(buffer, 0, requested, position);
|
|
599
|
+
if (bytesRead === 0) {
|
|
600
|
+
throw new Error('File ended while computing append proof');
|
|
601
|
+
}
|
|
602
|
+
const chunk = buffer.subarray(0, bytesRead);
|
|
603
|
+
fullHash.update(chunk);
|
|
604
|
+
const prefixBytes = Math.min(bytesRead, Math.max(0, prefixLength - position));
|
|
605
|
+
if (prefixBytes > 0) {
|
|
606
|
+
prefixHash.update(chunk.subarray(0, prefixBytes));
|
|
607
|
+
}
|
|
608
|
+
position += bytesRead;
|
|
609
|
+
}
|
|
610
|
+
await assertStableSnapshot();
|
|
611
|
+
return {
|
|
612
|
+
prefixDigest: prefixHash.digest('hex'),
|
|
613
|
+
fullDigest: fullHash.digest('hex'),
|
|
614
|
+
};
|
|
615
|
+
}
|
|
616
|
+
finally {
|
|
617
|
+
await handle.close();
|
|
618
|
+
}
|
|
270
619
|
}
|
|
271
620
|
toSourceRef(source, adapter) {
|
|
272
621
|
if (typeof source === 'string') {
|
|
@@ -279,12 +628,21 @@ let SessionCacheService = SessionCacheService_1 = class SessionCacheService {
|
|
|
279
628
|
return source;
|
|
280
629
|
}
|
|
281
630
|
async computeFreshness(ref, adapter) {
|
|
282
|
-
const { size, mtimeMs } = await this.statFile(ref.filePath);
|
|
283
|
-
const
|
|
631
|
+
const { size, mtimeMs, dev, ino, fileIdentity } = await this.statFile(ref.filePath);
|
|
632
|
+
const adapterToken = adapter.getFreshnessToken
|
|
284
633
|
? await adapter.getFreshnessToken(ref)
|
|
285
|
-
: { mtimeMs, size };
|
|
286
|
-
const
|
|
287
|
-
|
|
634
|
+
: { mtimeMs, size, dev, ino };
|
|
635
|
+
const token = ref.kind === 'file' && adapter.getFreshnessToken ? { adapterToken, dev, ino } : adapterToken;
|
|
636
|
+
const sourceVersion = ref.kind === 'db'
|
|
637
|
+
? this.dbSourceVersion(token, size)
|
|
638
|
+
: fileSourceVersion({ size, mtimeMs, dev, ino });
|
|
639
|
+
return {
|
|
640
|
+
token,
|
|
641
|
+
sourceVersion,
|
|
642
|
+
size,
|
|
643
|
+
mtimeMs,
|
|
644
|
+
fileIdentity: ref.kind === 'file' ? fileIdentity : undefined,
|
|
645
|
+
};
|
|
288
646
|
}
|
|
289
647
|
dbSourceVersion(token, fallbackSize) {
|
|
290
648
|
if (token && typeof token === 'object') {
|
|
@@ -298,6 +656,15 @@ let SessionCacheService = SessionCacheService_1 = class SessionCacheService {
|
|
|
298
656
|
};
|
|
299
657
|
exports.SessionCacheService = SessionCacheService;
|
|
300
658
|
exports.SessionCacheService = SessionCacheService = SessionCacheService_1 = __decorate([
|
|
301
|
-
(0, common_1.Injectable)()
|
|
659
|
+
(0, common_1.Injectable)(),
|
|
660
|
+
__param(1, (0, common_1.Optional)()),
|
|
661
|
+
__param(1, (0, common_1.Inject)(exports.TRANSCRIPT_CACHE_CONFIG)),
|
|
662
|
+
__metadata("design:paramtypes", [metrics_service_1.MetricsService, Object])
|
|
302
663
|
], SessionCacheService);
|
|
664
|
+
function positiveIntegerFromEnv(raw, fallback) {
|
|
665
|
+
if (raw === undefined)
|
|
666
|
+
return fallback;
|
|
667
|
+
const parsed = Number(raw);
|
|
668
|
+
return Number.isSafeInteger(parsed) && parsed > 0 ? parsed : fallback;
|
|
669
|
+
}
|
|
303
670
|
//# sourceMappingURL=session-cache.service.js.map
|