@monoes/monomindcli 2.8.4 → 2.9.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude/helpers/auto-memory-hook.mjs +0 -0
- package/.claude/helpers/handlers/route-handler.cjs +12 -0
- package/.claude/helpers/handlers/session-restore-handler.cjs +28 -7
- package/.claude/helpers/hook-handler.cjs +0 -0
- package/.claude/helpers/utils/micro-agents.cjs +22 -0
- package/.claude/skills/monodesign/scripts/live/sveltekit-adapter.mjs +11 -6
- package/.claude/skills/monodesign/scripts/live-inject.mjs +20 -7
- package/.claude/skills/monodesign/scripts/live-server.mjs +38 -2
- package/LICENSE +191 -0
- package/README.md +8 -6
- package/dist/src/browser/dashboard/server.d.ts +5 -0
- package/dist/src/browser/dashboard/server.d.ts.map +1 -1
- package/dist/src/browser/dashboard/server.js +59 -4
- package/dist/src/browser/dashboard/server.js.map +1 -1
- package/dist/src/browser/dashboard/ui.html +18 -8
- package/dist/src/browser/workflow/store.d.ts.map +1 -1
- package/dist/src/browser/workflow/store.js +3 -2
- package/dist/src/browser/workflow/store.js.map +1 -1
- package/dist/src/capabilities/cap-documents.d.ts.map +1 -1
- package/dist/src/capabilities/cap-documents.js +14 -9
- package/dist/src/capabilities/cap-documents.js.map +1 -1
- package/dist/src/commands/doctor.d.ts.map +1 -1
- package/dist/src/commands/doctor.js +22 -18
- package/dist/src/commands/doctor.js.map +1 -1
- package/dist/src/commands/download-embeddings.d.ts +8 -0
- package/dist/src/commands/download-embeddings.d.ts.map +1 -0
- package/dist/src/commands/download-embeddings.js +34 -0
- package/dist/src/commands/download-embeddings.js.map +1 -0
- package/dist/src/commands/hooks.d.ts.map +1 -1
- package/dist/src/commands/hooks.js +14 -0
- package/dist/src/commands/hooks.js.map +1 -1
- package/dist/src/commands/index.d.ts.map +1 -1
- package/dist/src/commands/index.js +4 -0
- package/dist/src/commands/index.js.map +1 -1
- package/dist/src/commands/init-wizard.js +1 -1
- package/dist/src/commands/init-wizard.js.map +1 -1
- package/dist/src/commands/init.d.ts.map +1 -1
- package/dist/src/commands/init.js +48 -1
- package/dist/src/commands/init.js.map +1 -1
- package/dist/src/commands/monograph.d.ts.map +1 -1
- package/dist/src/commands/monograph.js +35 -1
- package/dist/src/commands/monograph.js.map +1 -1
- package/dist/src/commands/org-observe.d.ts +10 -0
- package/dist/src/commands/org-observe.d.ts.map +1 -1
- package/dist/src/commands/org-observe.js +195 -31
- package/dist/src/commands/org-observe.js.map +1 -1
- package/dist/src/commands/org.d.ts +1 -0
- package/dist/src/commands/org.d.ts.map +1 -1
- package/dist/src/commands/org.js +139 -3
- package/dist/src/commands/org.js.map +1 -1
- package/dist/src/commands/route.d.ts +1 -9
- package/dist/src/commands/route.d.ts.map +1 -1
- package/dist/src/commands/route.js +42 -65
- package/dist/src/commands/route.js.map +1 -1
- package/dist/src/commands/security-cve.d.ts.map +1 -1
- package/dist/src/commands/security-cve.js +2 -1
- package/dist/src/commands/security-cve.js.map +1 -1
- package/dist/src/index.d.ts +0 -10
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +4 -15
- package/dist/src/index.js.map +1 -1
- package/dist/src/init/copy-assets.d.ts +17 -0
- package/dist/src/init/copy-assets.d.ts.map +1 -0
- package/dist/src/init/copy-assets.js +271 -0
- package/dist/src/init/copy-assets.js.map +1 -0
- package/dist/src/init/executor.d.ts +2 -30
- package/dist/src/init/executor.d.ts.map +1 -1
- package/dist/src/init/executor.js +56 -2493
- package/dist/src/init/executor.js.map +1 -1
- package/dist/src/init/helpers-generator.d.ts.map +1 -1
- package/dist/src/init/helpers-generator.js +9 -0
- package/dist/src/init/helpers-generator.js.map +1 -1
- package/dist/src/init/settings-generator.d.ts.map +1 -1
- package/dist/src/init/settings-generator.js +0 -4
- package/dist/src/init/settings-generator.js.map +1 -1
- package/dist/src/init/shared.d.ts +112 -0
- package/dist/src/init/shared.d.ts.map +1 -0
- package/dist/src/init/shared.js +475 -0
- package/dist/src/init/shared.js.map +1 -0
- package/dist/src/init/statusline-generator.d.ts.map +1 -1
- package/dist/src/init/statusline-generator.js +37 -0
- package/dist/src/init/statusline-generator.js.map +1 -1
- package/dist/src/init/types.d.ts +1 -1
- package/dist/src/init/types.d.ts.map +1 -1
- package/dist/src/init/upgrade.d.ts +34 -0
- package/dist/src/init/upgrade.d.ts.map +1 -0
- package/dist/src/init/upgrade.js +477 -0
- package/dist/src/init/upgrade.js.map +1 -0
- package/dist/src/init/write-antigravity.d.ts +13 -0
- package/dist/src/init/write-antigravity.d.ts.map +1 -0
- package/dist/src/init/write-antigravity.js +117 -0
- package/dist/src/init/write-antigravity.js.map +1 -0
- package/dist/src/init/write-capabilities.d.ts +9 -0
- package/dist/src/init/write-capabilities.d.ts.map +1 -0
- package/dist/src/init/write-capabilities.js +392 -0
- package/dist/src/init/write-capabilities.js.map +1 -0
- package/dist/src/init/write-claude.d.ts +25 -0
- package/dist/src/init/write-claude.d.ts.map +1 -0
- package/dist/src/init/write-claude.js +279 -0
- package/dist/src/init/write-claude.js.map +1 -0
- package/dist/src/init/write-kimicode.d.ts +19 -0
- package/dist/src/init/write-kimicode.d.ts.map +1 -0
- package/dist/src/init/write-kimicode.js +223 -0
- package/dist/src/init/write-kimicode.js.map +1 -0
- package/dist/src/init/write-opencode.d.ts +14 -0
- package/dist/src/init/write-opencode.d.ts.map +1 -0
- package/dist/src/init/write-opencode.js +130 -0
- package/dist/src/init/write-opencode.js.map +1 -0
- package/dist/src/init/write-runtime-config.d.ts +14 -0
- package/dist/src/init/write-runtime-config.d.ts.map +1 -0
- package/dist/src/init/write-runtime-config.js +214 -0
- package/dist/src/init/write-runtime-config.js.map +1 -0
- package/dist/src/init/write-sample-org.d.ts +9 -0
- package/dist/src/init/write-sample-org.d.ts.map +1 -0
- package/dist/src/init/write-sample-org.js +39 -0
- package/dist/src/init/write-sample-org.js.map +1 -0
- package/dist/src/knowledge/eval/golden-set.js +1 -1
- package/dist/src/knowledge/eval/golden-set.js.map +1 -1
- package/dist/src/mcp-tools/analyze-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/analyze-tools.js +2 -25
- package/dist/src/mcp-tools/analyze-tools.js.map +1 -1
- package/dist/src/mcp-tools/auto-install.d.ts.map +1 -1
- package/dist/src/mcp-tools/auto-install.js +2 -1
- package/dist/src/mcp-tools/auto-install.js.map +1 -1
- package/dist/src/mcp-tools/hooks-routing.d.ts.map +1 -1
- package/dist/src/mcp-tools/hooks-routing.js +26 -0
- package/dist/src/mcp-tools/hooks-routing.js.map +1 -1
- package/dist/src/mcp-tools/memory-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/memory-tools.js +2 -37
- package/dist/src/mcp-tools/memory-tools.js.map +1 -1
- package/dist/src/mcp-tools/monograph/agent-history-tools.d.ts +5 -0
- package/dist/src/mcp-tools/monograph/agent-history-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/agent-history-tools.js +177 -0
- package/dist/src/mcp-tools/monograph/agent-history-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/build-tools.d.ts +9 -0
- package/dist/src/mcp-tools/monograph/build-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/build-tools.js +299 -0
- package/dist/src/mcp-tools/monograph/build-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/group-tools.d.ts +10 -0
- package/dist/src/mcp-tools/monograph/group-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/group-tools.js +225 -0
- package/dist/src/mcp-tools/monograph/group-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/health-tools.d.ts +6 -0
- package/dist/src/mcp-tools/monograph/health-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/health-tools.js +113 -0
- package/dist/src/mcp-tools/monograph/health-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/impact-tools.d.ts +9 -0
- package/dist/src/mcp-tools/monograph/impact-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/impact-tools.js +532 -0
- package/dist/src/mcp-tools/monograph/impact-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/index.d.ts +10 -0
- package/dist/src/mcp-tools/monograph/index.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/index.js +73 -0
- package/dist/src/mcp-tools/monograph/index.js.map +1 -0
- package/dist/src/mcp-tools/monograph/query-tools.d.ts +11 -0
- package/dist/src/mcp-tools/monograph/query-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/query-tools.js +500 -0
- package/dist/src/mcp-tools/monograph/query-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph/shared.d.ts +64 -0
- package/dist/src/mcp-tools/monograph/shared.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/shared.js +215 -0
- package/dist/src/mcp-tools/monograph/shared.js.map +1 -0
- package/dist/src/mcp-tools/monograph/visualize-tools.d.ts +10 -0
- package/dist/src/mcp-tools/monograph/visualize-tools.d.ts.map +1 -0
- package/dist/src/mcp-tools/monograph/visualize-tools.js +382 -0
- package/dist/src/mcp-tools/monograph/visualize-tools.js.map +1 -0
- package/dist/src/mcp-tools/monograph-tools.d.ts +4 -23
- package/dist/src/mcp-tools/monograph-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/monograph-tools.js +4 -2439
- package/dist/src/mcp-tools/monograph-tools.js.map +1 -1
- package/dist/src/mcp-tools/monomind-tools.d.ts +8 -0
- package/dist/src/mcp-tools/monomind-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/monomind-tools.js +13 -1
- package/dist/src/mcp-tools/monomind-tools.js.map +1 -1
- package/dist/src/mcp-tools/quality/security-compliance/detect-secrets.d.ts.map +1 -1
- package/dist/src/mcp-tools/quality/security-compliance/detect-secrets.js +31 -2
- package/dist/src/mcp-tools/quality/security-compliance/detect-secrets.js.map +1 -1
- package/dist/src/mcp-tools/terminal-tools.d.ts.map +1 -1
- package/dist/src/mcp-tools/terminal-tools.js +31 -1
- package/dist/src/mcp-tools/terminal-tools.js.map +1 -1
- package/dist/src/mcp-tools/types.d.ts +8 -27
- package/dist/src/mcp-tools/types.d.ts.map +1 -1
- package/dist/src/mcp-tools/types.js +9 -91
- package/dist/src/mcp-tools/types.js.map +1 -1
- package/dist/src/memory/file-permissions.d.ts +15 -0
- package/dist/src/memory/file-permissions.d.ts.map +1 -0
- package/dist/src/memory/file-permissions.js +25 -0
- package/dist/src/memory/file-permissions.js.map +1 -0
- package/dist/src/memory/memory-bridge.d.ts.map +1 -1
- package/dist/src/memory/memory-bridge.js +94 -34
- package/dist/src/memory/memory-bridge.js.map +1 -1
- package/dist/src/memory/memory-crud.d.ts.map +1 -1
- package/dist/src/memory/memory-crud.js +298 -275
- package/dist/src/memory/memory-crud.js.map +1 -1
- package/dist/src/memory/memory-initializer.d.ts +2 -4
- package/dist/src/memory/memory-initializer.d.ts.map +1 -1
- package/dist/src/memory/memory-initializer.js +53 -76
- package/dist/src/memory/memory-initializer.js.map +1 -1
- package/dist/src/memory/memory-migrations.d.ts +1 -14
- package/dist/src/memory/memory-migrations.d.ts.map +1 -1
- package/dist/src/memory/memory-migrations.js +52 -105
- package/dist/src/memory/memory-migrations.js.map +1 -1
- package/dist/src/memory/sona-optimizer.d.ts +1 -1
- package/dist/src/memory/sona-optimizer.js +1 -1
- package/dist/src/monovector/index.d.ts +16 -19
- package/dist/src/monovector/index.d.ts.map +1 -1
- package/dist/src/monovector/index.js +50 -8
- package/dist/src/monovector/index.js.map +1 -1
- package/dist/src/orgrt/approvals.d.ts +16 -0
- package/dist/src/orgrt/approvals.d.ts.map +1 -0
- package/dist/src/orgrt/approvals.js +72 -0
- package/dist/src/orgrt/approvals.js.map +1 -0
- package/dist/src/orgrt/bus.d.ts.map +1 -1
- package/dist/src/orgrt/bus.js +21 -0
- package/dist/src/orgrt/bus.js.map +1 -1
- package/dist/src/orgrt/checkpoint-ops.d.ts +19 -0
- package/dist/src/orgrt/checkpoint-ops.d.ts.map +1 -0
- package/dist/src/orgrt/checkpoint-ops.js +219 -0
- package/dist/src/orgrt/checkpoint-ops.js.map +1 -0
- package/dist/src/orgrt/checkpoint.d.ts +33 -1
- package/dist/src/orgrt/checkpoint.d.ts.map +1 -1
- package/dist/src/orgrt/checkpoint.js +50 -6
- package/dist/src/orgrt/checkpoint.js.map +1 -1
- package/dist/src/orgrt/cross-org.d.ts +32 -0
- package/dist/src/orgrt/cross-org.d.ts.map +1 -0
- package/dist/src/orgrt/cross-org.js +256 -0
- package/dist/src/orgrt/cross-org.js.map +1 -0
- package/dist/src/orgrt/daemon.d.ts +131 -157
- package/dist/src/orgrt/daemon.d.ts.map +1 -1
- package/dist/src/orgrt/daemon.js +356 -966
- package/dist/src/orgrt/daemon.js.map +1 -1
- package/dist/src/orgrt/decisions.d.ts +33 -0
- package/dist/src/orgrt/decisions.d.ts.map +1 -0
- package/dist/src/orgrt/decisions.js +169 -0
- package/dist/src/orgrt/decisions.js.map +1 -0
- package/dist/src/orgrt/kimicode-runner.d.ts.map +1 -1
- package/dist/src/orgrt/kimicode-runner.js +5 -1
- package/dist/src/orgrt/kimicode-runner.js.map +1 -1
- package/dist/src/orgrt/opencode-runner.d.ts.map +1 -1
- package/dist/src/orgrt/opencode-runner.js +10 -2
- package/dist/src/orgrt/opencode-runner.js.map +1 -1
- package/dist/src/orgrt/org-memory.d.ts +45 -0
- package/dist/src/orgrt/org-memory.d.ts.map +1 -0
- package/dist/src/orgrt/org-memory.js +220 -0
- package/dist/src/orgrt/org-memory.js.map +1 -0
- package/dist/src/orgrt/policy.d.ts +4 -0
- package/dist/src/orgrt/policy.d.ts.map +1 -1
- package/dist/src/orgrt/policy.js +13 -1
- package/dist/src/orgrt/policy.js.map +1 -1
- package/dist/src/orgrt/prechecks.d.ts +15 -0
- package/dist/src/orgrt/prechecks.d.ts.map +1 -0
- package/dist/src/orgrt/prechecks.js +21 -0
- package/dist/src/orgrt/prechecks.js.map +1 -0
- package/dist/src/orgrt/questions.d.ts +39 -0
- package/dist/src/orgrt/questions.d.ts.map +1 -0
- package/dist/src/orgrt/questions.js +135 -0
- package/dist/src/orgrt/questions.js.map +1 -0
- package/dist/src/orgrt/remote.d.ts +25 -0
- package/dist/src/orgrt/remote.d.ts.map +1 -0
- package/dist/src/orgrt/remote.js +73 -0
- package/dist/src/orgrt/remote.js.map +1 -0
- package/dist/src/orgrt/scheduler-integration.d.ts +19 -0
- package/dist/src/orgrt/scheduler-integration.d.ts.map +1 -0
- package/dist/src/orgrt/scheduler-integration.js +90 -0
- package/dist/src/orgrt/scheduler-integration.js.map +1 -0
- package/dist/src/orgrt/server.d.ts.map +1 -1
- package/dist/src/orgrt/server.js +70 -2
- package/dist/src/orgrt/server.js.map +1 -1
- package/dist/src/orgrt/session.d.ts +30 -1
- package/dist/src/orgrt/session.d.ts.map +1 -1
- package/dist/src/orgrt/session.js +184 -53
- package/dist/src/orgrt/session.js.map +1 -1
- package/dist/src/orgrt/state-detector.d.ts +19 -0
- package/dist/src/orgrt/state-detector.d.ts.map +1 -0
- package/dist/src/orgrt/state-detector.js +59 -0
- package/dist/src/orgrt/state-detector.js.map +1 -0
- package/dist/src/orgrt/task-dag.d.ts +27 -0
- package/dist/src/orgrt/task-dag.d.ts.map +1 -0
- package/dist/src/orgrt/task-dag.js +100 -0
- package/dist/src/orgrt/task-dag.js.map +1 -0
- package/dist/src/orgrt/tool-fence.d.ts +7 -4
- package/dist/src/orgrt/tool-fence.d.ts.map +1 -1
- package/dist/src/orgrt/tool-fence.js +47 -6
- package/dist/src/orgrt/tool-fence.js.map +1 -1
- package/dist/src/orgrt/types.d.ts +57 -2
- package/dist/src/orgrt/types.d.ts.map +1 -1
- package/dist/src/orgrt/types.js +34 -3
- package/dist/src/orgrt/types.js.map +1 -1
- package/dist/src/routing/model-download.d.ts +49 -0
- package/dist/src/routing/model-download.d.ts.map +1 -0
- package/dist/src/routing/model-download.js +106 -0
- package/dist/src/routing/model-download.js.map +1 -0
- package/dist/src/services/crash-reporter.d.ts +5 -0
- package/dist/src/services/crash-reporter.d.ts.map +1 -1
- package/dist/src/services/crash-reporter.js +49 -0
- package/dist/src/services/crash-reporter.js.map +1 -1
- package/dist/src/transfer/anonymization/index.d.ts +18 -15
- package/dist/src/transfer/anonymization/index.d.ts.map +1 -1
- package/dist/src/transfer/anonymization/index.js +7 -119
- package/dist/src/transfer/anonymization/index.js.map +1 -1
- package/dist/src/ui/dashboard.html +606 -7
- package/dist/src/ui/orgs.html +7 -1
- package/dist/src/ui/routes-monograph.mjs +6 -0
- package/dist/src/ui/server.mjs +327 -7
- package/dist/src/update/checker.d.ts.map +1 -1
- package/dist/src/update/checker.js +2 -1
- package/dist/src/update/checker.js.map +1 -1
- package/dist/src/update/executor.d.ts.map +1 -1
- package/dist/src/update/executor.js +7 -3
- package/dist/src/update/executor.js.map +1 -1
- package/dist/src/update/index.d.ts +0 -1
- package/dist/src/update/index.d.ts.map +1 -1
- package/dist/src/update/index.js +5 -24
- package/dist/src/update/index.js.map +1 -1
- package/dist/src/utils/db-mutex.d.ts +11 -0
- package/dist/src/utils/db-mutex.d.ts.map +1 -0
- package/dist/src/utils/db-mutex.js +23 -0
- package/dist/src/utils/db-mutex.js.map +1 -0
- package/dist/src/utils/input-guards.d.ts +23 -0
- package/dist/src/utils/input-guards.d.ts.map +1 -1
- package/dist/src/utils/input-guards.js +72 -0
- package/dist/src/utils/input-guards.js.map +1 -1
- package/dist/src/utils/npm-command.d.ts +10 -0
- package/dist/src/utils/npm-command.d.ts.map +1 -0
- package/dist/src/utils/npm-command.js +12 -0
- package/dist/src/utils/npm-command.js.map +1 -0
- package/dist/src/utils/paths.d.ts +28 -0
- package/dist/src/utils/paths.d.ts.map +1 -0
- package/dist/src/utils/paths.js +108 -0
- package/dist/src/utils/paths.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +17 -17
- package/scripts/download-embedding-model.mjs +97 -0
- package/scripts/publish.sh +0 -0
- package/scripts/sync-claude-assets.sh +0 -0
- package/dist/src/production/circuit-breaker.d.ts +0 -121
- package/dist/src/production/circuit-breaker.d.ts.map +0 -1
- package/dist/src/production/circuit-breaker.js +0 -262
- package/dist/src/production/circuit-breaker.js.map +0 -1
- package/dist/src/production/error-handler.d.ts +0 -119
- package/dist/src/production/error-handler.d.ts.map +0 -1
- package/dist/src/production/error-handler.js +0 -324
- package/dist/src/production/error-handler.js.map +0 -1
- package/dist/src/production/index.d.ts +0 -6
- package/dist/src/production/index.d.ts.map +0 -1
- package/dist/src/production/index.js +0 -6
- package/dist/src/production/index.js.map +0 -1
- package/dist/src/production/monitoring.d.ts +0 -181
- package/dist/src/production/monitoring.d.ts.map +0 -1
- package/dist/src/production/monitoring.js +0 -375
- package/dist/src/production/monitoring.js.map +0 -1
- package/dist/src/production/rate-limiter.d.ts +0 -125
- package/dist/src/production/rate-limiter.d.ts.map +0 -1
- package/dist/src/production/rate-limiter.js +0 -218
- package/dist/src/production/rate-limiter.js.map +0 -1
- package/dist/src/production/retry.d.ts +0 -48
- package/dist/src/production/retry.d.ts.map +0 -1
- package/dist/src/production/retry.js +0 -189
- package/dist/src/production/retry.js.map +0 -1
- package/dist/src/transfer/types.d.ts +0 -245
- package/dist/src/transfer/types.d.ts.map +0 -1
- package/dist/src/transfer/types.js +0 -6
- package/dist/src/transfer/types.js.map +0 -1
|
@@ -11,6 +11,8 @@ import { safeParseEmbedding } from './memory-bridge.js';
|
|
|
11
11
|
import { ensureSchemaColumns } from './memory-migrations.js';
|
|
12
12
|
import { generateEmbedding } from './embedding-operations.js';
|
|
13
13
|
import { addToHNSWIndex, rebuildSearchIndex } from './hnsw-operations.js';
|
|
14
|
+
import { withDbLock } from '../utils/db-mutex.js';
|
|
15
|
+
import { secureDbFilePermissions } from './file-permissions.js';
|
|
14
16
|
// Re-export read operations so existing callers keep working without changes.
|
|
15
17
|
export { searchEntries, listEntries, getEntry } from './memory-read.js';
|
|
16
18
|
/** Maximum SQLite database file size accepted before read (256 MB). */
|
|
@@ -39,163 +41,166 @@ export async function verifyMemoryInit(dbPath, options) {
|
|
|
39
41
|
const { verbose = false } = options || {};
|
|
40
42
|
const tests = [];
|
|
41
43
|
try {
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
44
|
+
return await withDbLock(dbPath, async () => {
|
|
45
|
+
const initSqlJs = (await import('sql.js')).default;
|
|
46
|
+
const SQL = await initSqlJs();
|
|
47
|
+
const fs = await import('fs');
|
|
48
|
+
// Guard against excessively large DB files to prevent OOM.
|
|
49
|
+
const verifyStat = fs.statSync(dbPath);
|
|
50
|
+
if (verifyStat.size > MAX_DB_FILE_BYTES) {
|
|
51
|
+
return { success: false, tests: [{ name: 'Database access', passed: false, details: `File too large: ${verifyStat.size} bytes` }], summary: { passed: 0, failed: 1, total: 1 } };
|
|
52
|
+
}
|
|
53
|
+
// Load database
|
|
54
|
+
const fileBuffer = fs.readFileSync(dbPath);
|
|
55
|
+
const db = new SQL.Database(fileBuffer);
|
|
56
|
+
// Test 1: Schema verification
|
|
57
|
+
const schemaStart = Date.now();
|
|
58
|
+
const tables = db.exec("SELECT name FROM sqlite_master WHERE type='table'");
|
|
59
|
+
const tableNames = tables[0]?.values?.map(v => v[0]) || [];
|
|
60
|
+
const expectedTables = ['memory_entries', 'patterns', 'metadata', 'vector_indexes'];
|
|
61
|
+
const missingTables = expectedTables.filter(t => !tableNames.includes(t));
|
|
62
|
+
tests.push({
|
|
63
|
+
name: 'Schema verification',
|
|
64
|
+
passed: missingTables.length === 0,
|
|
65
|
+
details: missingTables.length > 0 ? `Missing: ${missingTables.join(', ')}` : `${tableNames.length} tables found`,
|
|
66
|
+
duration: Date.now() - schemaStart
|
|
67
|
+
});
|
|
68
|
+
// Test 2: Write entry
|
|
69
|
+
const writeStart = Date.now();
|
|
70
|
+
const testId = `test_${Date.now()}`;
|
|
71
|
+
const testKey = 'verification_test';
|
|
72
|
+
const testValue = 'This is a verification test entry for memory initialization';
|
|
73
|
+
try {
|
|
74
|
+
db.run(`
|
|
72
75
|
INSERT INTO memory_entries (id, key, namespace, content, type, created_at, updated_at)
|
|
73
76
|
VALUES (?, ?, 'test', ?, 'semantic', ?, ?)
|
|
74
77
|
`, [testId, testKey, testValue, Date.now(), Date.now()]);
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
78
|
+
tests.push({
|
|
79
|
+
name: 'Write entry',
|
|
80
|
+
passed: true,
|
|
81
|
+
details: 'Entry written successfully',
|
|
82
|
+
duration: Date.now() - writeStart
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
catch (e) {
|
|
86
|
+
tests.push({
|
|
87
|
+
name: 'Write entry',
|
|
88
|
+
passed: false,
|
|
89
|
+
details: e instanceof Error ? e.message : 'Write failed',
|
|
90
|
+
duration: Date.now() - writeStart
|
|
91
|
+
});
|
|
92
|
+
}
|
|
93
|
+
// Test 3: Read entry
|
|
94
|
+
const readStart = Date.now();
|
|
95
|
+
try {
|
|
96
|
+
const result = db.exec(`SELECT content FROM memory_entries WHERE id = ?`, [testId]);
|
|
97
|
+
const content = result[0]?.values[0]?.[0];
|
|
98
|
+
tests.push({
|
|
99
|
+
name: 'Read entry',
|
|
100
|
+
passed: content === testValue,
|
|
101
|
+
details: content === testValue ? 'Content matches' : 'Content mismatch',
|
|
102
|
+
duration: Date.now() - readStart
|
|
103
|
+
});
|
|
104
|
+
}
|
|
105
|
+
catch (e) {
|
|
106
|
+
tests.push({
|
|
107
|
+
name: 'Read entry',
|
|
108
|
+
passed: false,
|
|
109
|
+
details: e instanceof Error ? e.message : 'Read failed',
|
|
110
|
+
duration: Date.now() - readStart
|
|
111
|
+
});
|
|
112
|
+
}
|
|
113
|
+
// Test 4: Write with embedding
|
|
114
|
+
const embeddingStart = Date.now();
|
|
115
|
+
try {
|
|
116
|
+
const { embedding, dimensions, model } = await generateEmbedding(testValue);
|
|
117
|
+
const embeddingJson = JSON.stringify(embedding);
|
|
118
|
+
db.run(`
|
|
116
119
|
UPDATE memory_entries
|
|
117
120
|
SET embedding = ?, embedding_dimensions = ?, embedding_model = ?
|
|
118
121
|
WHERE id = ?
|
|
119
122
|
`, [embeddingJson, dimensions, model, testId]);
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
123
|
+
tests.push({
|
|
124
|
+
name: 'Generate embedding',
|
|
125
|
+
passed: true,
|
|
126
|
+
details: `${dimensions}-dim vector (${model})`,
|
|
127
|
+
duration: Date.now() - embeddingStart
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
catch (e) {
|
|
131
|
+
tests.push({
|
|
132
|
+
name: 'Generate embedding',
|
|
133
|
+
passed: false,
|
|
134
|
+
details: e instanceof Error ? e.message : 'Embedding failed',
|
|
135
|
+
duration: Date.now() - embeddingStart
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
// Test 5: Pattern storage
|
|
139
|
+
const patternStart = Date.now();
|
|
140
|
+
try {
|
|
141
|
+
const patternId = `pattern_${Date.now()}`;
|
|
142
|
+
db.run(`
|
|
140
143
|
INSERT INTO patterns (id, name, pattern_type, condition, action, confidence, created_at, updated_at)
|
|
141
144
|
VALUES (?, 'test-pattern', 'task-routing', 'test condition', 'test action', 0.5, ?, ?)
|
|
142
145
|
`, [patternId, Date.now(), Date.now()]);
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
}
|
|
152
|
-
catch (e) {
|
|
153
|
-
tests.push({
|
|
154
|
-
name: 'Pattern storage',
|
|
155
|
-
passed: false,
|
|
156
|
-
details: e instanceof Error ? e.message : 'Pattern storage failed',
|
|
157
|
-
duration: Date.now() - patternStart
|
|
158
|
-
});
|
|
159
|
-
}
|
|
160
|
-
// Test 6: Vector index configuration
|
|
161
|
-
const indexStart = Date.now();
|
|
162
|
-
try {
|
|
163
|
-
const indexResult = db.exec(`SELECT name, dimensions, hnsw_m, hnsw_ef_construction FROM vector_indexes`);
|
|
164
|
-
const indexes = indexResult[0]?.values || [];
|
|
165
|
-
tests.push({
|
|
166
|
-
name: 'Vector index config',
|
|
167
|
-
passed: indexes.length > 0,
|
|
168
|
-
details: `${indexes.length} indexes configured (HNSW M=16, ef=200)`,
|
|
169
|
-
duration: Date.now() - indexStart
|
|
170
|
-
});
|
|
171
|
-
}
|
|
172
|
-
catch (e) {
|
|
173
|
-
tests.push({
|
|
174
|
-
name: 'Vector index config',
|
|
175
|
-
passed: false,
|
|
176
|
-
details: e instanceof Error ? e.message : 'Index check failed',
|
|
177
|
-
duration: Date.now() - indexStart
|
|
178
|
-
});
|
|
179
|
-
}
|
|
180
|
-
// Cleanup test entry
|
|
181
|
-
db.run(`DELETE FROM memory_entries WHERE id = ?`, [testId]);
|
|
182
|
-
// Save changes atomically
|
|
183
|
-
const data = db.export();
|
|
184
|
-
const dbTmpHealth = dbPath + '.tmp';
|
|
185
|
-
fs.writeFileSync(dbTmpHealth, Buffer.from(data));
|
|
186
|
-
fs.renameSync(dbTmpHealth, dbPath);
|
|
187
|
-
db.close();
|
|
188
|
-
const passed = tests.filter(t => t.passed).length;
|
|
189
|
-
const failed = tests.filter(t => !t.passed).length;
|
|
190
|
-
return {
|
|
191
|
-
success: failed === 0,
|
|
192
|
-
tests,
|
|
193
|
-
summary: {
|
|
194
|
-
passed,
|
|
195
|
-
failed,
|
|
196
|
-
total: tests.length
|
|
146
|
+
tests.push({
|
|
147
|
+
name: 'Pattern storage',
|
|
148
|
+
passed: true,
|
|
149
|
+
details: 'Pattern stored with confidence scoring',
|
|
150
|
+
duration: Date.now() - patternStart
|
|
151
|
+
});
|
|
152
|
+
// Cleanup test pattern
|
|
153
|
+
db.run(`DELETE FROM patterns WHERE id = ?`, [patternId]);
|
|
197
154
|
}
|
|
198
|
-
|
|
155
|
+
catch (e) {
|
|
156
|
+
tests.push({
|
|
157
|
+
name: 'Pattern storage',
|
|
158
|
+
passed: false,
|
|
159
|
+
details: e instanceof Error ? e.message : 'Pattern storage failed',
|
|
160
|
+
duration: Date.now() - patternStart
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
// Test 6: Vector index configuration
|
|
164
|
+
const indexStart = Date.now();
|
|
165
|
+
try {
|
|
166
|
+
const indexResult = db.exec(`SELECT name, dimensions, hnsw_m, hnsw_ef_construction FROM vector_indexes`);
|
|
167
|
+
const indexes = indexResult[0]?.values || [];
|
|
168
|
+
tests.push({
|
|
169
|
+
name: 'Vector index config',
|
|
170
|
+
passed: indexes.length > 0,
|
|
171
|
+
details: `${indexes.length} indexes configured (HNSW M=16, ef=200)`,
|
|
172
|
+
duration: Date.now() - indexStart
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
catch (e) {
|
|
176
|
+
tests.push({
|
|
177
|
+
name: 'Vector index config',
|
|
178
|
+
passed: false,
|
|
179
|
+
details: e instanceof Error ? e.message : 'Index check failed',
|
|
180
|
+
duration: Date.now() - indexStart
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
// Cleanup test entry
|
|
184
|
+
db.run(`DELETE FROM memory_entries WHERE id = ?`, [testId]);
|
|
185
|
+
// Save changes atomically
|
|
186
|
+
const data = db.export();
|
|
187
|
+
const dbTmpHealth = dbPath + '.tmp';
|
|
188
|
+
fs.writeFileSync(dbTmpHealth, Buffer.from(data));
|
|
189
|
+
fs.renameSync(dbTmpHealth, dbPath);
|
|
190
|
+
secureDbFilePermissions(dbPath);
|
|
191
|
+
db.close();
|
|
192
|
+
const passed = tests.filter(t => t.passed).length;
|
|
193
|
+
const failed = tests.filter(t => !t.passed).length;
|
|
194
|
+
return {
|
|
195
|
+
success: failed === 0,
|
|
196
|
+
tests,
|
|
197
|
+
summary: {
|
|
198
|
+
passed,
|
|
199
|
+
failed,
|
|
200
|
+
total: tests.length
|
|
201
|
+
}
|
|
202
|
+
};
|
|
203
|
+
});
|
|
199
204
|
}
|
|
200
205
|
catch (error) {
|
|
201
206
|
return {
|
|
@@ -230,97 +235,112 @@ export async function storeEntry(options) {
|
|
|
230
235
|
return { success: false, id: '', error: 'Database not initialized. Run: monomind memory init' };
|
|
231
236
|
}
|
|
232
237
|
await ensureSchemaColumns(dbPath);
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
const fileBuffer = fs.readFileSync(dbPath);
|
|
240
|
-
const db = new SQL.Database(fileBuffer);
|
|
241
|
-
// memory_entries has no UNIQUE constraint on (key, namespace) — only
|
|
242
|
-
// `id TEXT PRIMARY KEY`. `INSERT OR REPLACE` only replaces a row when
|
|
243
|
-
// its PRIMARY KEY collides, so generating a fresh id on every call (as
|
|
244
|
-
// this used to do unconditionally) meant upsert never actually matched
|
|
245
|
-
// the existing row for a given key+namespace — it silently inserted a
|
|
246
|
-
// duplicate instead of replacing it. When upserting, look up the
|
|
247
|
-
// existing row's real id first and reuse it so the replace actually
|
|
248
|
-
// collides; only mint a new id when no existing row is found.
|
|
249
|
-
let id = `entry_${Date.now()}_${Math.random().toString(36).substring(7)}`;
|
|
250
|
-
let existingCreatedAt = null;
|
|
251
|
-
if (upsert) {
|
|
252
|
-
// Only match active rows — a soft-deleted row's key+namespace should
|
|
253
|
-
// not be resurrected by an unrelated upsert; that would both restore
|
|
254
|
-
// history a delete intentionally cleared and mask the deletion.
|
|
255
|
-
const existingIdResult = db.exec("SELECT id, created_at FROM memory_entries WHERE key = ? AND namespace = ? AND status = 'active' LIMIT 1", [key, namespace]);
|
|
256
|
-
const existingRow = existingIdResult[0]?.values?.[0];
|
|
257
|
-
const existingId = existingRow?.[0];
|
|
258
|
-
if (typeof existingId === 'string') {
|
|
259
|
-
id = existingId;
|
|
260
|
-
const createdAt = existingRow?.[1];
|
|
261
|
-
if (typeof createdAt === 'number')
|
|
262
|
-
existingCreatedAt = createdAt;
|
|
238
|
+
return await withDbLock(dbPath, async () => {
|
|
239
|
+
const initSqlJs = (await import('sql.js')).default;
|
|
240
|
+
const SQL = await initSqlJs();
|
|
241
|
+
const storeStat = fs.statSync(dbPath);
|
|
242
|
+
if (storeStat.size > MAX_DB_FILE_BYTES) {
|
|
243
|
+
return { success: false, id: '', error: `Database file too large: ${storeStat.size} bytes` };
|
|
263
244
|
}
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
245
|
+
const fileBuffer = fs.readFileSync(dbPath);
|
|
246
|
+
const db = new SQL.Database(fileBuffer);
|
|
247
|
+
let id = `entry_${Date.now()}_${Math.random().toString(36).substring(7)}`;
|
|
248
|
+
let existingCreatedAt = null;
|
|
249
|
+
let matchedExisting = false;
|
|
250
|
+
if (upsert) {
|
|
251
|
+
const existingIdResult = db.exec("SELECT id, created_at FROM memory_entries WHERE key = ? AND namespace = ? AND status = 'active' LIMIT 1", [key, namespace]);
|
|
252
|
+
const existingRow = existingIdResult[0]?.values?.[0];
|
|
253
|
+
const existingId = existingRow?.[0];
|
|
254
|
+
if (typeof existingId === 'string') {
|
|
255
|
+
id = existingId;
|
|
256
|
+
matchedExisting = true;
|
|
257
|
+
const createdAt = existingRow?.[1];
|
|
258
|
+
if (typeof createdAt === 'number')
|
|
259
|
+
existingCreatedAt = createdAt;
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
const now = Date.now();
|
|
263
|
+
const createdAt = existingCreatedAt ?? now;
|
|
264
|
+
let embeddingJson = null;
|
|
265
|
+
let embeddingDimensions = null;
|
|
266
|
+
let embeddingModel = null;
|
|
267
|
+
if (generateEmbeddingFlag && value.length > 0) {
|
|
268
|
+
const embResult = await generateEmbedding(value);
|
|
269
|
+
embeddingJson = JSON.stringify(embResult.embedding);
|
|
270
|
+
embeddingDimensions = embResult.dimensions;
|
|
271
|
+
embeddingModel = embResult.model;
|
|
272
|
+
}
|
|
273
|
+
const isUpdate = upsert && matchedExisting;
|
|
274
|
+
if (isUpdate) {
|
|
275
|
+
// #88: upsert against an existing row must UPDATE in place. The old
|
|
276
|
+
// INSERT OR REPLACE omitted access_count, confidence, importance_score,
|
|
277
|
+
// last_accessed_at, owner_id, agent_id, session_id and hardcoded
|
|
278
|
+
// metadata '{}' — every update silently wiped all learned stats.
|
|
279
|
+
db.run(`UPDATE memory_entries SET
|
|
280
|
+
content = ?,
|
|
281
|
+
embedding = ?,
|
|
282
|
+
embedding_dimensions = ?,
|
|
283
|
+
embedding_model = ?,
|
|
284
|
+
tags = ?,
|
|
285
|
+
updated_at = ?,
|
|
286
|
+
expires_at = ?
|
|
287
|
+
WHERE id = ?`, [
|
|
288
|
+
value,
|
|
289
|
+
embeddingJson,
|
|
290
|
+
embeddingDimensions,
|
|
291
|
+
embeddingModel,
|
|
292
|
+
tags.length > 0 ? JSON.stringify(tags) : null,
|
|
293
|
+
now,
|
|
294
|
+
ttl ? now + (ttl * 1000) : null,
|
|
295
|
+
id
|
|
296
|
+
]);
|
|
297
|
+
}
|
|
298
|
+
else {
|
|
299
|
+
const insertSql = `INSERT INTO memory_entries (
|
|
283
300
|
id, key, namespace, content, type,
|
|
284
301
|
embedding, embedding_dimensions, embedding_model,
|
|
285
302
|
tags, metadata, created_at, updated_at, expires_at, status
|
|
286
303
|
) VALUES (?, ?, ?, ?, 'semantic', ?, ?, ?, ?, ?, ?, ?, ?, 'active')`;
|
|
287
|
-
|
|
288
|
-
id,
|
|
289
|
-
key,
|
|
290
|
-
namespace,
|
|
291
|
-
value,
|
|
292
|
-
embeddingJson,
|
|
293
|
-
embeddingDimensions,
|
|
294
|
-
embeddingModel,
|
|
295
|
-
tags.length > 0 ? JSON.stringify(tags) : null,
|
|
296
|
-
'{}',
|
|
297
|
-
createdAt,
|
|
298
|
-
now,
|
|
299
|
-
ttl ? now + (ttl * 1000) : null
|
|
300
|
-
]);
|
|
301
|
-
// Save atomically
|
|
302
|
-
const data = db.export();
|
|
303
|
-
const dbTmpStore = dbPath + '.tmp';
|
|
304
|
-
fs.writeFileSync(dbTmpStore, Buffer.from(data));
|
|
305
|
-
fs.renameSync(dbTmpStore, dbPath);
|
|
306
|
-
db.close();
|
|
307
|
-
// Add to HNSW index for faster future searches
|
|
308
|
-
if (embeddingJson) {
|
|
309
|
-
const embResult = safeParseEmbedding(embeddingJson);
|
|
310
|
-
if (embResult) {
|
|
311
|
-
await addToHNSWIndex(id, embResult, {
|
|
304
|
+
db.run(insertSql, [
|
|
312
305
|
id,
|
|
313
306
|
key,
|
|
314
307
|
namespace,
|
|
315
|
-
|
|
316
|
-
|
|
308
|
+
value,
|
|
309
|
+
embeddingJson,
|
|
310
|
+
embeddingDimensions,
|
|
311
|
+
embeddingModel,
|
|
312
|
+
tags.length > 0 ? JSON.stringify(tags) : null,
|
|
313
|
+
'{}',
|
|
314
|
+
createdAt,
|
|
315
|
+
now,
|
|
316
|
+
ttl ? now + (ttl * 1000) : null
|
|
317
|
+
]);
|
|
317
318
|
}
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
319
|
+
// Save atomically
|
|
320
|
+
const data = db.export();
|
|
321
|
+
const dbTmpStore = dbPath + '.tmp';
|
|
322
|
+
fs.writeFileSync(dbTmpStore, Buffer.from(data));
|
|
323
|
+
fs.renameSync(dbTmpStore, dbPath);
|
|
324
|
+
secureDbFilePermissions(dbPath);
|
|
325
|
+
db.close();
|
|
326
|
+
// Add to HNSW index for faster future searches
|
|
327
|
+
if (embeddingJson) {
|
|
328
|
+
const embResult = safeParseEmbedding(embeddingJson);
|
|
329
|
+
if (embResult) {
|
|
330
|
+
await addToHNSWIndex(id, embResult, {
|
|
331
|
+
id,
|
|
332
|
+
key,
|
|
333
|
+
namespace,
|
|
334
|
+
content: value
|
|
335
|
+
});
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
return {
|
|
339
|
+
success: true,
|
|
340
|
+
id,
|
|
341
|
+
embedding: embeddingJson ? { dimensions: embeddingDimensions, model: embeddingModel } : undefined
|
|
342
|
+
};
|
|
343
|
+
});
|
|
324
344
|
}
|
|
325
345
|
catch (error) {
|
|
326
346
|
return {
|
|
@@ -378,42 +398,43 @@ export async function deleteEntry(options) {
|
|
|
378
398
|
};
|
|
379
399
|
}
|
|
380
400
|
await ensureSchemaColumns(dbPath);
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
401
|
+
return await withDbLock(dbPath, async () => {
|
|
402
|
+
const initSqlJs = (await import('sql.js')).default;
|
|
403
|
+
const SQL = await initSqlJs();
|
|
404
|
+
const deleteStat = fs.statSync(dbPath);
|
|
405
|
+
if (deleteStat.size > MAX_DB_FILE_BYTES) {
|
|
406
|
+
return { success: false, deleted: false, key, namespace, remainingEntries: 0, error: `Database file too large: ${deleteStat.size} bytes` };
|
|
407
|
+
}
|
|
408
|
+
const fileBuffer = fs.readFileSync(dbPath);
|
|
409
|
+
const db = new SQL.Database(fileBuffer);
|
|
410
|
+
const checkStmt = db.prepare(`
|
|
390
411
|
SELECT id FROM memory_entries
|
|
391
412
|
WHERE status = 'active'
|
|
392
413
|
AND key = ?
|
|
393
414
|
AND namespace = ?
|
|
394
415
|
LIMIT 1
|
|
395
416
|
`);
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
+
checkStmt.bind([key, namespace]);
|
|
418
|
+
const checkRows = [];
|
|
419
|
+
while (checkStmt.step()) {
|
|
420
|
+
checkRows.push(checkStmt.get());
|
|
421
|
+
}
|
|
422
|
+
checkStmt.free();
|
|
423
|
+
const checkResult = checkRows.length > 0 ? [{ values: checkRows }] : [];
|
|
424
|
+
if (!checkResult[0]?.values?.[0]) {
|
|
425
|
+
const countResult = db.exec(`SELECT COUNT(*) FROM memory_entries WHERE status = 'active'`);
|
|
426
|
+
const remainingEntries = countResult[0]?.values?.[0]?.[0] || 0;
|
|
427
|
+
db.close();
|
|
428
|
+
return {
|
|
429
|
+
success: true,
|
|
430
|
+
deleted: false,
|
|
431
|
+
key,
|
|
432
|
+
namespace,
|
|
433
|
+
remainingEntries,
|
|
434
|
+
error: `Key '${key}' not found in namespace '${namespace}'`
|
|
435
|
+
};
|
|
436
|
+
}
|
|
437
|
+
db.run(`
|
|
417
438
|
UPDATE memory_entries
|
|
418
439
|
SET status = 'deleted',
|
|
419
440
|
embedding = NULL,
|
|
@@ -422,23 +443,25 @@ export async function deleteEntry(options) {
|
|
|
422
443
|
AND namespace = ?
|
|
423
444
|
AND status = 'active'
|
|
424
445
|
`, [key, namespace]);
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
446
|
+
const countResult = db.exec(`SELECT COUNT(*) FROM memory_entries WHERE status = 'active'`);
|
|
447
|
+
const remainingEntries = countResult[0]?.values?.[0]?.[0] || 0;
|
|
448
|
+
// Save updated database atomically
|
|
449
|
+
const data = db.export();
|
|
450
|
+
const dbTmpDelete = dbPath + '.tmp';
|
|
451
|
+
fs.writeFileSync(dbTmpDelete, Buffer.from(data));
|
|
452
|
+
fs.renameSync(dbTmpDelete, dbPath);
|
|
453
|
+
secureDbFilePermissions(dbPath);
|
|
454
|
+
db.close();
|
|
455
|
+
// Invalidate the HNSW index so it rebuilds from DB on next search.
|
|
456
|
+
rebuildSearchIndex();
|
|
457
|
+
return {
|
|
458
|
+
success: true,
|
|
459
|
+
deleted: true,
|
|
460
|
+
key,
|
|
461
|
+
namespace,
|
|
462
|
+
remainingEntries
|
|
463
|
+
};
|
|
464
|
+
});
|
|
442
465
|
}
|
|
443
466
|
catch (error) {
|
|
444
467
|
return {
|