create-walle 0.9.21 → 0.9.23
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 +27 -5
- package/package.json +2 -2
- package/template/CLAUDE.md +2 -2
- package/template/LICENSE +1 -1
- package/template/bin/ctm-dev-cleanup.js +24 -3
- package/template/bin/ctm-launch.sh +13 -0
- package/template/bin/dev.sh +156 -18
- package/template/bin/node-bin.sh +84 -0
- package/template/bin/pin-node.sh +51 -0
- package/template/claude-task-manager/api-prompts.js +1203 -182
- package/template/claude-task-manager/api-reviews.js +109 -15
- package/template/claude-task-manager/approval-agent.js +1360 -280
- package/template/claude-task-manager/bin/restart-ctm.sh +64 -23
- package/template/claude-task-manager/bin/storage-migration-supervisor.js +338 -0
- package/template/claude-task-manager/db.js +4417 -295
- package/template/claude-task-manager/docs/app-update-refresh-protocol.md +69 -0
- package/template/claude-task-manager/docs/approval-ai-refinement.md +138 -0
- package/template/claude-task-manager/docs/approval-rescue-loop.md +74 -0
- package/template/claude-task-manager/docs/codex-operational-warning-health.md +107 -0
- package/template/claude-task-manager/docs/codex-resume-state-guard-design.md +17 -12
- package/template/claude-task-manager/docs/codex-terminal-render-controller-handoff.md +311 -0
- package/template/claude-task-manager/docs/coding-agent-hooks-architecture.md +418 -0
- package/template/claude-task-manager/docs/conversation-import-freshness.md +20 -0
- package/template/claude-task-manager/docs/google-workspace-auth-health.md +77 -0
- package/template/claude-task-manager/docs/image-paste-ux.md +13 -0
- package/template/claude-task-manager/docs/ipad-web-preview.md +88 -0
- package/template/claude-task-manager/docs/main-loop-offload-architecture.md +66 -0
- package/template/claude-task-manager/docs/microsoft-dev-tunnel-phone-access-design.md +274 -519
- package/template/claude-task-manager/docs/mobile-live-streaming.md +27 -5
- package/template/claude-task-manager/docs/mobile-remote-submission-lifecycle.md +69 -0
- package/template/claude-task-manager/docs/phone-access-design.md +53 -15
- package/template/claude-task-manager/docs/phone-passkey-identity.md +122 -0
- package/template/claude-task-manager/docs/phone-setup.md +3 -0
- package/template/claude-task-manager/docs/prompt-editing-tree-design.md +25 -1
- package/template/claude-task-manager/docs/remote-desktop-access-design.md +268 -0
- package/template/claude-task-manager/docs/restart-lifecycle-architecture.md +95 -0
- package/template/claude-task-manager/docs/runtime-work-control-plane.md +53 -0
- package/template/claude-task-manager/docs/session-interactive-wait-surfaces.md +38 -0
- package/template/claude-task-manager/docs/session-needs-you-dismissal.md +84 -0
- package/template/claude-task-manager/docs/session-render-state-management-design.md +91 -3
- package/template/claude-task-manager/docs/session-standup-command-center-design.md +25 -1
- package/template/claude-task-manager/docs/session-title-authority.md +32 -0
- package/template/claude-task-manager/docs/session-workspace-binding.md +33 -0
- package/template/claude-task-manager/docs/skill-intent-resolution-design.md +72 -0
- package/template/claude-task-manager/docs/walle-mcp-supervisor-health.md +86 -0
- package/template/claude-task-manager/docs/walle-relay-phone-access-design.md +24 -15
- package/template/claude-task-manager/docs/walle-session-history-hydration.md +114 -0
- package/template/claude-task-manager/docs/walle-session-input-queue.md +104 -0
- package/template/claude-task-manager/docs/walle-session-model-catalog.md +90 -0
- package/template/claude-task-manager/docs/walle-session-model-preferences.md +15 -6
- package/template/claude-task-manager/git-utils.js +897 -27
- package/template/claude-task-manager/lib/agent-capabilities.js +33 -0
- package/template/claude-task-manager/lib/agent-cli-cache.js +37 -7
- package/template/claude-task-manager/lib/agent-hooks-installer.js +26 -2
- package/template/claude-task-manager/lib/agent-presets.js +17 -1
- package/template/claude-task-manager/lib/all-sessions-query.js +108 -0
- package/template/claude-task-manager/lib/approval-ai-refinement.js +488 -0
- package/template/claude-task-manager/lib/approval-self-adapt.js +168 -0
- package/template/claude-task-manager/lib/async-semaphore.js +44 -0
- package/template/claude-task-manager/lib/auth-context.js +5 -0
- package/template/claude-task-manager/lib/auth-rate-limit.js +47 -4
- package/template/claude-task-manager/lib/auth-rules.js +29 -2
- package/template/claude-task-manager/lib/auto-approval-verifier.js +129 -16
- package/template/claude-task-manager/lib/background-llm.js +144 -17
- package/template/claude-task-manager/lib/branch-inventory.js +212 -0
- package/template/claude-task-manager/lib/claude-desktop-sessions.js +15 -3
- package/template/claude-task-manager/lib/coalesce-sync-frames.js +151 -0
- package/template/claude-task-manager/lib/codex-launch-health.js +762 -0
- package/template/claude-task-manager/lib/codex-transcript-pager.js +51 -0
- package/template/claude-task-manager/lib/codex-zst.js +124 -0
- package/template/claude-task-manager/lib/coding-agent-models.js +233 -30
- package/template/claude-task-manager/lib/connection-health.js +232 -0
- package/template/claude-task-manager/lib/conversation-blob-parser.js +42 -0
- package/template/claude-task-manager/lib/conversation-tail-merge.js +89 -26
- package/template/claude-task-manager/lib/ctm-session-context-api.js +39 -10
- package/template/claude-task-manager/lib/cursor-conversation-store.js +354 -0
- package/template/claude-task-manager/lib/db-owner-worker-client.js +315 -0
- package/template/claude-task-manager/lib/document-review.js +141 -6
- package/template/claude-task-manager/lib/escalation-review.js +152 -0
- package/template/claude-task-manager/lib/graceful-shutdown.js +159 -0
- package/template/claude-task-manager/lib/headless-term-service.js +678 -0
- package/template/claude-task-manager/lib/heavy-worker-fallback.js +38 -0
- package/template/claude-task-manager/lib/jsonl-conversation-parser.js +542 -0
- package/template/claude-task-manager/lib/jsonl-range-reader.js +112 -0
- package/template/claude-task-manager/lib/main-db-census.js +216 -0
- package/template/claude-task-manager/lib/message-pagination.js +106 -4
- package/template/claude-task-manager/lib/microsoft-dev-tunnel-setup.js +750 -26
- package/template/claude-task-manager/lib/mobile-auth-api.js +274 -7
- package/template/claude-task-manager/lib/mobile-auth-store.js +592 -10
- package/template/claude-task-manager/lib/mobile-notification-dispatcher.js +15 -0
- package/template/claude-task-manager/lib/model-overview-brain-fallback.js +311 -0
- package/template/claude-task-manager/lib/model-overview-cache.js +141 -0
- package/template/claude-task-manager/lib/models-health-routing-notice.js +126 -0
- package/template/claude-task-manager/lib/node-pin-guard.js +93 -0
- package/template/claude-task-manager/lib/perf-tracker.js +242 -6
- package/template/claude-task-manager/lib/permission-match.js +76 -0
- package/template/claude-task-manager/lib/permission-sync.js +133 -20
- package/template/claude-task-manager/lib/process-title.js +35 -0
- package/template/claude-task-manager/lib/prompt-executions-query.js +25 -0
- package/template/claude-task-manager/lib/prompt-index-disk-cache.js +44 -0
- package/template/claude-task-manager/lib/prompt-intent.js +132 -0
- package/template/claude-task-manager/lib/provider-user-context.js +34 -0
- package/template/claude-task-manager/lib/read-pool-client.js +313 -0
- package/template/claude-task-manager/lib/readpool-breaker.js +31 -0
- package/template/claude-task-manager/lib/recent-sessions-breaker.js +12 -0
- package/template/claude-task-manager/lib/remote-feedback-client.js +72 -0
- package/template/claude-task-manager/lib/remote-relay-protocol.js +37 -4
- package/template/claude-task-manager/lib/remote-relay-store.js +159 -0
- package/template/claude-task-manager/lib/remote-submission-observer.js +278 -0
- package/template/claude-task-manager/lib/restart-guard.js +109 -0
- package/template/claude-task-manager/lib/restore-interruption-detector.js +439 -0
- package/template/claude-task-manager/lib/restore-policy.js +13 -0
- package/template/claude-task-manager/lib/restore-resume-batch.js +74 -0
- package/template/claude-task-manager/lib/restore-runtime.js +68 -0
- package/template/claude-task-manager/lib/restore-storm.js +34 -0
- package/template/claude-task-manager/lib/resume-cwd.js +36 -0
- package/template/claude-task-manager/lib/resume-preflight.js +313 -0
- package/template/claude-task-manager/lib/runtime-work-registry.js +444 -0
- package/template/claude-task-manager/lib/sanitize-openai-auth.js +31 -0
- package/template/claude-task-manager/lib/scheduler.js +21 -1
- package/template/claude-task-manager/lib/scrollback-snapshot-store.js +159 -0
- package/template/claude-task-manager/lib/serial-task-queue.js +64 -0
- package/template/claude-task-manager/lib/server-listeners.js +239 -0
- package/template/claude-task-manager/lib/session-capture.js +42 -7
- package/template/claude-task-manager/lib/session-content-backfill.js +131 -0
- package/template/claude-task-manager/lib/session-history.js +388 -43
- package/template/claude-task-manager/lib/session-host-manager.js +287 -0
- package/template/claude-task-manager/lib/session-image-refs.js +209 -0
- package/template/claude-task-manager/lib/session-jobs.js +399 -59
- package/template/claude-task-manager/lib/session-prompt-index.js +137 -0
- package/template/claude-task-manager/lib/session-restore.js +53 -0
- package/template/claude-task-manager/lib/session-standup.js +123 -23
- package/template/claude-task-manager/lib/session-state-bus.js +14 -0
- package/template/claude-task-manager/lib/session-stream.js +64 -16
- package/template/claude-task-manager/lib/session-timeline-summary.js +260 -0
- package/template/claude-task-manager/lib/session-token-usage.js +494 -0
- package/template/claude-task-manager/lib/session-workspace-binding.js +356 -0
- package/template/claude-task-manager/lib/setup-network-config.js +9 -0
- package/template/claude-task-manager/lib/size-cap.js +45 -0
- package/template/claude-task-manager/lib/size-cap.test.js +62 -0
- package/template/claude-task-manager/lib/skill-autocomplete.js +180 -1
- package/template/claude-task-manager/lib/skill-intent-resolver.js +304 -0
- package/template/claude-task-manager/lib/sqlite-driver.js +19 -3
- package/template/claude-task-manager/lib/standup-attention.js +7 -3
- package/template/claude-task-manager/lib/status-authority.js +39 -0
- package/template/claude-task-manager/lib/status-hooks.js +4 -0
- package/template/claude-task-manager/lib/storage-migration.js +235 -0
- package/template/claude-task-manager/lib/structured-capture.js +298 -0
- package/template/claude-task-manager/lib/sync-io-census.js +163 -0
- package/template/claude-task-manager/lib/tailscale-setup.js +6 -0
- package/template/claude-task-manager/lib/terminal-activity-evidence.js +33 -0
- package/template/claude-task-manager/lib/terminal-choice.js +364 -0
- package/template/claude-task-manager/lib/terminal-control-sanitize.js +17 -0
- package/template/claude-task-manager/lib/terminal-fingerprint.js +48 -0
- package/template/claude-task-manager/lib/terminal-output-flush.js +84 -0
- package/template/claude-task-manager/lib/timeline-order.js +122 -0
- package/template/claude-task-manager/lib/transcript-store.js +348 -43
- package/template/claude-task-manager/lib/transport-security.js +84 -1
- package/template/claude-task-manager/lib/wait-state.js +184 -0
- package/template/claude-task-manager/lib/walle-client.js +47 -5
- package/template/claude-task-manager/lib/walle-ctm-history.js +564 -4
- package/template/claude-task-manager/lib/walle-external-actions.js +135 -16
- package/template/claude-task-manager/lib/walle-history-hydration.js +46 -0
- package/template/claude-task-manager/lib/walle-native-health.js +403 -0
- package/template/claude-task-manager/lib/walle-repair.js +701 -0
- package/template/claude-task-manager/lib/walle-session-cache.js +109 -0
- package/template/claude-task-manager/lib/walle-session-context.js +57 -21
- package/template/claude-task-manager/lib/walle-session-model-catalog.js +34 -0
- package/template/claude-task-manager/lib/walle-supervisor.js +539 -63
- package/template/claude-task-manager/lib/walle-transcript.js +52 -0
- package/template/claude-task-manager/lib/worktree-active-sync.js +11 -7
- package/template/claude-task-manager/lib/worktree-cwd.js +32 -1
- package/template/claude-task-manager/package.json +1 -1
- package/template/claude-task-manager/prompt-harvest.js +89 -66
- package/template/claude-task-manager/providers/claude-code.js +51 -3
- package/template/claude-task-manager/providers/cursor.js +140 -45
- package/template/claude-task-manager/public/css/reviews.css +551 -61
- package/template/claude-task-manager/public/css/setup.css +191 -0
- package/template/claude-task-manager/public/css/walle-session.css +865 -10
- package/template/claude-task-manager/public/css/walle.css +154 -0
- package/template/claude-task-manager/public/designs/ai-providers-consolidation-v2.html +830 -0
- package/template/claude-task-manager/public/index.html +18516 -2058
- package/template/claude-task-manager/public/ipad.html +363 -0
- package/template/claude-task-manager/public/js/document-review-links.js +301 -0
- package/template/claude-task-manager/public/js/image-normalize.js +69 -36
- package/template/claude-task-manager/public/js/message-renderer.js +1265 -77
- package/template/claude-task-manager/public/js/prompts.js +66 -29
- package/template/claude-task-manager/public/js/reviews.js +901 -133
- package/template/claude-task-manager/public/js/session-activity-utils.js +11 -1
- package/template/claude-task-manager/public/js/session-search-utils.js +94 -10
- package/template/claude-task-manager/public/js/session-status-precedence.js +23 -5
- package/template/claude-task-manager/public/js/setup.js +1273 -176
- package/template/claude-task-manager/public/js/stream-view.js +691 -73
- package/template/claude-task-manager/public/js/terminal-reconciler.js +210 -0
- package/template/claude-task-manager/public/js/walle-session.js +2455 -158
- package/template/claude-task-manager/public/js/walle.js +455 -28
- package/template/claude-task-manager/public/m/app.css +2909 -262
- package/template/claude-task-manager/public/m/app.js +6601 -398
- package/template/claude-task-manager/public/m/claim.html +224 -17
- package/template/claude-task-manager/public/m/index.html +117 -21
- package/template/claude-task-manager/public/m/sw.js +3 -1
- package/template/claude-task-manager/public/manifest.json +2 -2
- package/template/claude-task-manager/public/prompts.html +30 -14
- package/template/claude-task-manager/queue-engine.js +507 -28
- package/template/claude-task-manager/scripts/repair-claude-session-images.js +27 -8
- package/template/claude-task-manager/server.js +14341 -2197
- package/template/claude-task-manager/session-integrity.js +160 -18
- package/template/claude-task-manager/session-search-ranking.js +1 -0
- package/template/claude-task-manager/session-utils.js +25 -5
- package/template/claude-task-manager/workers/approval-blocklist.js +96 -6
- package/template/claude-task-manager/workers/approval-widget-validator.js +14 -8
- package/template/claude-task-manager/workers/conversation-import-worker.js +11 -50
- package/template/claude-task-manager/workers/db-owner-worker.js +386 -0
- package/template/claude-task-manager/workers/harvest-worker.js +9 -55
- package/template/claude-task-manager/workers/headless-term-worker.js +9 -530
- package/template/claude-task-manager/workers/read-pool-worker.js +387 -0
- package/template/claude-task-manager/workers/scrollback-worker.js +11 -72
- package/template/claude-task-manager/workers/session-host-process.js +146 -0
- package/template/claude-task-manager/workers/session-integrity-worker.js +10 -54
- package/template/claude-task-manager/workers/state-detectors/base.js +18 -1
- package/template/claude-task-manager/workers/state-detectors/claude-code.js +182 -9
- package/template/claude-task-manager/workers/state-detectors/codex.js +150 -2
- package/template/claude-task-manager/workers/state-detectors/cursor.js +127 -0
- package/template/claude-task-manager/workers/state-detectors/gemini.js +21 -0
- package/template/claude-task-manager/workers/state-detectors/index.js +29 -0
- package/template/claude-task-manager/workers/state-detectors/opencode.js +103 -0
- package/template/docs/design/markdown-review-pane.md +206 -0
- package/template/docs/designs/2026-05-17-portkey-gateway-provider-ux.md +129 -38
- package/template/docs/designs/2026-05-20-mobile-worktree-finish-command.md +27 -0
- package/template/docs/designs/2026-05-22-ai-configuration-consolidation.md +248 -0
- package/template/docs/designs/ai-configuration-consolidation-mock.html +812 -0
- package/template/docs/private-memory-and-pii-policy.md +69 -0
- package/template/package.json +2 -1
- package/template/scripts/check-private-data.js +201 -0
- package/template/shared/sqlite-owner-guard.js +30 -0
- package/template/shared/sqlite-owner-write-queue.js +225 -0
- package/template/shared/sqlite-storage-policy.js +111 -0
- package/template/shared/sqlite-write-lock.js +428 -0
- package/template/wall-e/agent-runners/claude-code.js +5 -0
- package/template/wall-e/agent.js +166 -22
- package/template/wall-e/api-walle.js +524 -70
- package/template/wall-e/auth/provider-flows.js +11 -1
- package/template/wall-e/bin/walle-mcp-stdio.js +341 -17
- package/template/wall-e/brain.js +1614 -141
- package/template/wall-e/chat/attachment-blocks.js +96 -0
- package/template/wall-e/chat/attachments.js +2 -1
- package/template/wall-e/chat/capability-resolver.js +7 -7
- package/template/wall-e/chat/context-messages.js +28 -0
- package/template/wall-e/chat/conversation-frame.js +630 -0
- package/template/wall-e/chat/provider-messages.js +125 -0
- package/template/wall-e/chat.js +1002 -233
- package/template/wall-e/coding/acceptance-contract.js +170 -0
- package/template/wall-e/coding/acp-adapter.js +1 -1
- package/template/wall-e/coding/agent-catalog.js +3 -0
- package/template/wall-e/coding/artifact-store.js +93 -0
- package/template/wall-e/coding/capability-router.js +120 -0
- package/template/wall-e/coding/coding-run-controller.js +423 -0
- package/template/wall-e/coding/compaction-service.js +157 -12
- package/template/wall-e/coding/frontend-verification.js +258 -0
- package/template/wall-e/coding/lifecycle-hooks.js +75 -0
- package/template/wall-e/coding/local-preview-contract.js +157 -0
- package/template/wall-e/coding/permission-service.js +57 -13
- package/template/wall-e/coding/prompt-bundle.js +19 -1
- package/template/wall-e/coding/prompt-section-registry.js +227 -0
- package/template/wall-e/coding/provider-compat.js +15 -0
- package/template/wall-e/coding/runtime-events.js +224 -0
- package/template/wall-e/coding/runtime-mode.js +3 -0
- package/template/wall-e/coding/side-git-snapshot.js +160 -4
- package/template/wall-e/coding/snapshot-service.js +143 -1
- package/template/wall-e/coding/stream-processor.js +388 -34
- package/template/wall-e/coding/task-tool.js +141 -4
- package/template/wall-e/coding/tool-execution-controller.js +365 -0
- package/template/wall-e/coding/tool-registry.js +43 -5
- package/template/wall-e/coding/user-hooks.js +217 -0
- package/template/wall-e/coding-orchestrator.js +1330 -221
- package/template/wall-e/coding-prompts.js +20 -4
- package/template/wall-e/context/context-builder.js +15 -2
- package/template/wall-e/decision/confidence.js +1 -1
- package/template/wall-e/docs/coding-acceptance-contract.md +41 -0
- package/template/wall-e/docs/external-action-controller.md +26 -6
- package/template/wall-e/docs/telemetry-lifecycle.md +8 -2
- package/template/wall-e/embeddings.js +591 -53
- package/template/wall-e/external-action-controller.js +12 -0
- package/template/wall-e/http/auth.js +1 -0
- package/template/wall-e/http/chat-api.js +46 -11
- package/template/wall-e/http/model-admin.js +836 -34
- package/template/wall-e/lib/boot-profile.js +88 -0
- package/template/wall-e/lib/event-loop-monitor.js +93 -0
- package/template/wall-e/lib/service-health.js +194 -0
- package/template/wall-e/llm/anthropic.js +130 -5
- package/template/wall-e/llm/client.js +266 -63
- package/template/wall-e/llm/default-fallback.js +382 -0
- package/template/wall-e/llm/health.js +19 -0
- package/template/wall-e/llm/message-guard.js +78 -0
- package/template/wall-e/llm/model-catalog.js +252 -1
- package/template/wall-e/llm/openai.js +26 -4
- package/template/wall-e/llm/portkey-sync.js +654 -0
- package/template/wall-e/llm/provider-error.js +30 -2
- package/template/wall-e/llm/registry.js +5 -1
- package/template/wall-e/llm/request-compat.js +67 -0
- package/template/wall-e/loops/backfill.js +79 -23
- package/template/wall-e/loops/brain-optimize.js +67 -0
- package/template/wall-e/loops/ingest.js +25 -10
- package/template/wall-e/loops/question-digest.js +160 -0
- package/template/wall-e/loops/reflect.js +6 -4
- package/template/wall-e/loops/think.js +39 -12
- package/template/wall-e/mcp-server.js +318 -36
- package/template/wall-e/memory/ctm-context-client.js +52 -14
- package/template/wall-e/memory/ctm-operational-context.js +237 -0
- package/template/wall-e/memory/ctm-prompt-executions-client.js +128 -0
- package/template/wall-e/memory/ctm-session-context.js +111 -63
- package/template/wall-e/prompts/coding/deepseek.txt +3 -0
- package/template/wall-e/prompts/coding/gemini.txt +6 -0
- package/template/wall-e/prompts/coding/gpt.txt +6 -0
- package/template/wall-e/prompts/coding/local.txt +7 -0
- package/template/wall-e/runtime/decision-hooks.js +115 -0
- package/template/wall-e/runtime/devbox-gateway.js +82 -8
- package/template/wall-e/runtime/prompt-manifest.js +86 -0
- package/template/wall-e/runtime/tool-executor.js +269 -0
- package/template/wall-e/runtime/tool-result-envelope.js +138 -0
- package/template/wall-e/runtime/transcript-projection.js +60 -0
- package/template/wall-e/runtime/walle-runtime.js +224 -0
- package/template/wall-e/scripts/db-optimize/migrate.js +162 -0
- package/template/wall-e/scripts/db-optimize/recall-eval.js +117 -0
- package/template/wall-e/server.js +15 -0
- package/template/wall-e/session-files.js +9 -0
- package/template/wall-e/skills/_bundled/google-calendar/run.js +1 -1
- package/template/wall-e/skills/_bundled/gws-workspace/run.js +1 -1
- package/template/wall-e/skills/_bundled/slack-mentions/run.js +76 -6
- package/template/wall-e/skills/claude-code-reader.js +7 -3
- package/template/wall-e/skills/script-skill-runner.js +10 -0
- package/template/wall-e/skills/skill-planner.js +38 -0
- package/template/wall-e/tools/builtin-middleware.js +19 -9
- package/template/wall-e/tools/local-tools.js +1428 -16
- package/template/wall-e/tools/permission-checker.js +73 -5
- package/template/wall-e/tools/question-manager.js +117 -7
- package/template/wall-e/training/harvester.js +12 -28
- package/template/wall-e/training/replay.js +25 -80
- package/template/website/index.html +10 -10
- package/template/wall-e/eval/ab-test.js +0 -203
- package/template/wall-e/eval/agent-runner.js +0 -772
- package/template/wall-e/eval/agent-scorer.js +0 -461
- package/template/wall-e/eval/aggregator.js +0 -414
- package/template/wall-e/eval/allowed-test-commands.js +0 -34
- package/template/wall-e/eval/benchmark-generator.js +0 -113
- package/template/wall-e/eval/benchmarks/chat-eval.json +0 -1662
- package/template/wall-e/eval/benchmarks/chat.json +0 -82
- package/template/wall-e/eval/benchmarks/coding-agent-real.json +0 -1
- package/template/wall-e/eval/benchmarks/coding-agent.json +0 -1581
- package/template/wall-e/eval/benchmarks/coding.json +0 -122
- package/template/wall-e/eval/benchmarks/memory-retrieval.json +0 -234
- package/template/wall-e/eval/benchmarks/reasoning.json +0 -82
- package/template/wall-e/eval/benchmarks/swebench-lite-30.json +0 -212
- package/template/wall-e/eval/benchmarks.js +0 -669
- package/template/wall-e/eval/cc-replay.js +0 -719
- package/template/wall-e/eval/chat-eval.js +0 -525
- package/template/wall-e/eval/check-keys.js +0 -15
- package/template/wall-e/eval/check-providers.js +0 -42
- package/template/wall-e/eval/codex-cli-baseline.js +0 -669
- package/template/wall-e/eval/coding-agent-real.js +0 -570
- package/template/wall-e/eval/context-compactor.js +0 -251
- package/template/wall-e/eval/debug-agent003.js +0 -68
- package/template/wall-e/eval/diagnostics.js +0 -216
- package/template/wall-e/eval/eval-orchestrator.js +0 -642
- package/template/wall-e/eval/evaluate.js +0 -202
- package/template/wall-e/eval/evaluator.js +0 -373
- package/template/wall-e/eval/exporter.js +0 -212
- package/template/wall-e/eval/fixtures/express-basic/package.json +0 -9
- package/template/wall-e/eval/fixtures/express-basic/server.js +0 -115
- package/template/wall-e/eval/fixtures/express-basic/test.js +0 -83
- package/template/wall-e/eval/fixtures/express-buggy/package.json +0 -9
- package/template/wall-e/eval/fixtures/express-buggy/server.js +0 -113
- package/template/wall-e/eval/fixtures/express-buggy/test.js +0 -83
- package/template/wall-e/eval/fixtures/express-buggy-items/package.json +0 -9
- package/template/wall-e/eval/fixtures/express-buggy-items/server.js +0 -112
- package/template/wall-e/eval/fixtures/express-buggy-items/test.js +0 -83
- package/template/wall-e/eval/fixtures/express-buggy-search/package.json +0 -9
- package/template/wall-e/eval/fixtures/express-buggy-search/server.js +0 -121
- package/template/wall-e/eval/fixtures/express-buggy-search/test.js +0 -83
- package/template/wall-e/eval/fixtures/express-rename-data/data.js +0 -34
- package/template/wall-e/eval/fixtures/express-rename-data/package.json +0 -9
- package/template/wall-e/eval/fixtures/express-rename-data/server.js +0 -97
- package/template/wall-e/eval/fixtures/express-rename-data/test.js +0 -88
- package/template/wall-e/eval/fixtures/express-xss/package.json +0 -12
- package/template/wall-e/eval/fixtures/express-xss/server.js +0 -90
- package/template/wall-e/eval/fixtures/express-xss/test.js +0 -67
- package/template/wall-e/eval/fixtures/express-xss/views/profile.ejs +0 -9
- package/template/wall-e/eval/fixtures/fullstack-app/config/default.js +0 -9
- package/template/wall-e/eval/fixtures/fullstack-app/config/test.js +0 -13
- package/template/wall-e/eval/fixtures/fullstack-app/package.json +0 -11
- package/template/wall-e/eval/fixtures/fullstack-app/public/css/style.css +0 -137
- package/template/wall-e/eval/fixtures/fullstack-app/public/index.html +0 -46
- package/template/wall-e/eval/fixtures/fullstack-app/public/js/app.js +0 -121
- package/template/wall-e/eval/fixtures/fullstack-app/public/js/auth.js +0 -71
- package/template/wall-e/eval/fixtures/fullstack-app/public/js/items.js +0 -80
- package/template/wall-e/eval/fixtures/fullstack-app/public/js/users.js +0 -46
- package/template/wall-e/eval/fixtures/fullstack-app/public/login.html +0 -45
- package/template/wall-e/eval/fixtures/fullstack-app/public/register.html +0 -38
- package/template/wall-e/eval/fixtures/fullstack-app/scripts/migrate.js +0 -23
- package/template/wall-e/eval/fixtures/fullstack-app/scripts/seed.js +0 -46
- package/template/wall-e/eval/fixtures/fullstack-app/server/db.js +0 -99
- package/template/wall-e/eval/fixtures/fullstack-app/server/index.js +0 -94
- package/template/wall-e/eval/fixtures/fullstack-app/server/middleware/auth.js +0 -19
- package/template/wall-e/eval/fixtures/fullstack-app/server/middleware/logger.js +0 -19
- package/template/wall-e/eval/fixtures/fullstack-app/server/router.js +0 -50
- package/template/wall-e/eval/fixtures/fullstack-app/server/routes/auth.js +0 -69
- package/template/wall-e/eval/fixtures/fullstack-app/server/routes/health.js +0 -23
- package/template/wall-e/eval/fixtures/fullstack-app/server/routes/items.js +0 -88
- package/template/wall-e/eval/fixtures/fullstack-app/server/routes/users.js +0 -75
- package/template/wall-e/eval/fixtures/fullstack-app/server/test.js +0 -198
- package/template/wall-e/eval/fixtures/fullstack-app/server/utils/response.js +0 -34
- package/template/wall-e/eval/fixtures/fullstack-app/server/utils/validate.js +0 -26
- package/template/wall-e/eval/fixtures/fullstack-app/server.js +0 -8
- package/template/wall-e/eval/fixtures/fullstack-app/test.js +0 -12
- package/template/wall-e/eval/fixtures/monorepo-basic/package.json +0 -8
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/data.js +0 -58
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/middleware.js +0 -46
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/package.json +0 -8
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/routes.js +0 -64
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/server.js +0 -56
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/api/test.js +0 -116
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/cli/commands.js +0 -61
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/cli/index.js +0 -62
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/cli/output.js +0 -43
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/cli/package.json +0 -11
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/cli/test.js +0 -44
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/shared/formatters.js +0 -43
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/shared/index.js +0 -12
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/shared/package.json +0 -5
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/shared/test.js +0 -55
- package/template/wall-e/eval/fixtures/monorepo-basic/packages/shared/validators.js +0 -29
- package/template/wall-e/eval/fixtures/monorepo-basic/test.js +0 -46
- package/template/wall-e/eval/fixtures/node-cli/index.js +0 -78
- package/template/wall-e/eval/fixtures/node-cli/package.json +0 -10
- package/template/wall-e/eval/fixtures/node-cli/test.js +0 -57
- package/template/wall-e/eval/fixtures/node-typed/package.json +0 -8
- package/template/wall-e/eval/fixtures/node-typed/src/handlers.js +0 -31
- package/template/wall-e/eval/fixtures/node-typed/src/utils.js +0 -33
- package/template/wall-e/eval/fixtures/node-typed/test.js +0 -36
- package/template/wall-e/eval/fixtures/python-flask/app.py +0 -14
- package/template/wall-e/eval/fixtures/python-flask/requirements.txt +0 -2
- package/template/wall-e/eval/fixtures/python-flask/test_app.py +0 -25
- package/template/wall-e/eval/fixtures/wall-e-subset/brain.js +0 -105
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/aggregator.js +0 -101
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/benchmarks/chat.json +0 -20
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/benchmarks/coding.json +0 -32
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/benchmarks.js +0 -64
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/fixtures/simple-project/package.json +0 -6
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/fixtures/simple-project/server.js +0 -31
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/fixtures/simple-project/test.js +0 -18
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/fixtures/simple-project/utils.js +0 -34
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/runner.js +0 -104
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/scorer.js +0 -73
- package/template/wall-e/eval/fixtures/wall-e-subset/eval/test.js +0 -134
- package/template/wall-e/eval/fixtures/wall-e-subset/llm/client.js +0 -99
- package/template/wall-e/eval/fixtures/wall-e-subset/llm/providers.js +0 -63
- package/template/wall-e/eval/fixtures/wall-e-subset/llm/test.js +0 -70
- package/template/wall-e/eval/fixtures/wall-e-subset/package.json +0 -10
- package/template/wall-e/eval/fixtures/wall-e-subset/test.js +0 -86
- package/template/wall-e/eval/harvester.js +0 -685
- package/template/wall-e/eval/head-to-head.js +0 -388
- package/template/wall-e/eval/humaneval-adapter.js +0 -321
- package/template/wall-e/eval/list-models.js +0 -31
- package/template/wall-e/eval/livecodebench-adapter.js +0 -291
- package/template/wall-e/eval/mail-integration.js +0 -443
- package/template/wall-e/eval/manifest.js +0 -186
- package/template/wall-e/eval/meta-harness/adapters/coding-agent.js +0 -57
- package/template/wall-e/eval/meta-harness/bootstrap-snapshot.js +0 -149
- package/template/wall-e/eval/meta-harness/candidate-store.js +0 -117
- package/template/wall-e/eval/meta-harness/cli.js +0 -86
- package/template/wall-e/eval/meta-harness/domain-spec.js +0 -154
- package/template/wall-e/eval/meta-harness/domains/coding-agent.domain.json +0 -84
- package/template/wall-e/eval/meta-harness/examples/env-bootstrap-candidate.js +0 -29
- package/template/wall-e/eval/meta-harness/experience-store.js +0 -174
- package/template/wall-e/eval/meta-harness/frontier.js +0 -96
- package/template/wall-e/eval/meta-harness/harness-interface.js +0 -90
- package/template/wall-e/eval/meta-harness/leakage-guard.js +0 -80
- package/template/wall-e/eval/meta-harness/optimizer.js +0 -207
- package/template/wall-e/eval/meta-harness/proposer-runner.js +0 -110
- package/template/wall-e/eval/meta-harness/reporting.js +0 -58
- package/template/wall-e/eval/meta-harness/telemetry.js +0 -27
- package/template/wall-e/eval/meta-harness/validation.js +0 -81
- package/template/wall-e/eval/promoter.js +0 -228
- package/template/wall-e/eval/provider-normalizer.js +0 -33
- package/template/wall-e/eval/replay.js +0 -395
- package/template/wall-e/eval/run-agent-benchmarks.js +0 -386
- package/template/wall-e/eval/run-codex-cli-baseline.js +0 -177
- package/template/wall-e/eval/run-coding-agent-real.js +0 -187
- package/template/wall-e/eval/run-eval.js +0 -435
- package/template/wall-e/eval/run-model-comparison.js +0 -142
- package/template/wall-e/eval/session-evaluator.js +0 -187
- package/template/wall-e/eval/session-miner.js +0 -207
- package/template/wall-e/eval/session-retrieval-benchmark.js +0 -150
- package/template/wall-e/eval/session-transcripts.js +0 -509
- package/template/wall-e/eval/shadow.js +0 -161
- package/template/wall-e/eval/swebench-adapter.js +0 -345
- package/template/wall-e/eval/swebench-docker.js +0 -192
- package/template/wall-e/eval/train.py +0 -320
- package/template/wall-e/eval/trainer.js +0 -232
- package/template/wall-e/eval/weekly-eval-loop.js +0 -241
|
@@ -8,6 +8,29 @@ try { embeddings = require('../embeddings'); } catch { embeddings = null; }
|
|
|
8
8
|
|
|
9
9
|
const BATCH_SIZE = 20;
|
|
10
10
|
|
|
11
|
+
// Contradiction → question policy. Historically EVERY detected contradiction created a
|
|
12
|
+
// pending_question AND superseded the old knowledge — yielding ~2,000 questions/day that
|
|
13
|
+
// piled up (125k unanswered) because contradictions are mostly routine knowledge churn
|
|
14
|
+
// (working dir / current task / tool changed). We now ALWAYS supersede (newer wins) and
|
|
15
|
+
// only ask the owner when the contradiction is genuinely ambiguous. The offline detector
|
|
16
|
+
// flags mechanical churn (value_conflict / relationship_mismatch / stale_fact = "X was A,
|
|
17
|
+
// now B"); the LLM path is only invoked for the ambiguous remainder. So: ask only on
|
|
18
|
+
// LLM-detected contradictions (no offline `type`) or when the new fact's confidence is low.
|
|
19
|
+
const _OFFLINE_CONTRADICTION_TYPES = new Set(['value_conflict', 'relationship_mismatch', 'stale_fact']);
|
|
20
|
+
const _ASK_CONTRADICTION_CONFIDENCE = Number(process.env.WALL_E_ASK_CONTRADICTION_CONFIDENCE || 0.4);
|
|
21
|
+
function _contradictionQuestionsEnabled() {
|
|
22
|
+
return String(process.env.WALL_E_CONTRADICTION_QUESTIONS || 'on').toLowerCase() !== 'off';
|
|
23
|
+
}
|
|
24
|
+
function _shouldAskAboutContradiction(c) {
|
|
25
|
+
if (!c) return false;
|
|
26
|
+
if (c.type && _OFFLINE_CONTRADICTION_TYPES.has(c.type)) {
|
|
27
|
+
// Mechanical churn → supersede silently, unless the NEW fact itself is low-confidence.
|
|
28
|
+
const conf = Number(c.new_entry && c.new_entry.confidence);
|
|
29
|
+
return Number.isFinite(conf) && conf < _ASK_CONTRADICTION_CONFIDENCE;
|
|
30
|
+
}
|
|
31
|
+
return true; // LLM-detected (ambiguous) → ask
|
|
32
|
+
}
|
|
33
|
+
|
|
11
34
|
async function runOnce(opts = {}) {
|
|
12
35
|
// Centralized precheck: provider availability. (We don't pass
|
|
13
36
|
// hasFreshSignal here because think.js still does work — self-resolve
|
|
@@ -74,20 +97,24 @@ async function runOnce(opts = {}) {
|
|
|
74
97
|
e.object === contradiction.new_entry.object
|
|
75
98
|
);
|
|
76
99
|
|
|
77
|
-
//
|
|
78
|
-
brain.insertQuestion({
|
|
79
|
-
question_type: 'contradiction',
|
|
80
|
-
question: contradiction.explanation,
|
|
81
|
-
context: JSON.stringify({
|
|
82
|
-
old_id: contradiction.old_id,
|
|
83
|
-
new_entry: contradiction.new_entry,
|
|
84
|
-
}),
|
|
85
|
-
});
|
|
86
|
-
|
|
87
|
-
// Supersede old knowledge
|
|
100
|
+
// Always supersede old knowledge (newer wins) — keeps the graph current.
|
|
88
101
|
if (newInserted) {
|
|
89
102
|
brain.supersedeKnowledge(contradiction.old_id, newInserted._id);
|
|
90
103
|
}
|
|
104
|
+
|
|
105
|
+
// Only surface a question when genuinely worth the owner's input. Routine churn
|
|
106
|
+
// is superseded silently above (see _shouldAskAboutContradiction) — this stops the
|
|
107
|
+
// ~2,000/day pile-up while still escalating ambiguous/low-confidence conflicts.
|
|
108
|
+
if (_contradictionQuestionsEnabled() && _shouldAskAboutContradiction(contradiction)) {
|
|
109
|
+
brain.insertQuestion({
|
|
110
|
+
question_type: 'contradiction',
|
|
111
|
+
question: contradiction.explanation,
|
|
112
|
+
context: JSON.stringify({
|
|
113
|
+
old_id: contradiction.old_id,
|
|
114
|
+
new_entry: contradiction.new_entry,
|
|
115
|
+
}),
|
|
116
|
+
});
|
|
117
|
+
}
|
|
91
118
|
}
|
|
92
119
|
|
|
93
120
|
// Apply domain/topic classifications to memories
|
|
@@ -189,4 +216,4 @@ async function selfResolveQuestions(ownerName, opts = {}) {
|
|
|
189
216
|
}
|
|
190
217
|
}
|
|
191
218
|
|
|
192
|
-
module.exports = { runOnce };
|
|
219
|
+
module.exports = { runOnce, _shouldAskAboutContradiction };
|
|
@@ -6,6 +6,7 @@ const brain = require('./brain');
|
|
|
6
6
|
const { createSessionIngestService } = require('./memory/session-ingest-service');
|
|
7
7
|
const ctmSessionContext = require('./memory/ctm-session-context');
|
|
8
8
|
const ctmContextClient = require('./memory/ctm-context-client');
|
|
9
|
+
const ctmOperationalContext = require('./memory/ctm-operational-context');
|
|
9
10
|
const { collectIngestRecords } = require('./sources/base');
|
|
10
11
|
const { ensureBuiltinSourceAdapters } = require('./sources/builtin');
|
|
11
12
|
const sourceRegistry = require('./sources/registry');
|
|
@@ -192,6 +193,8 @@ const TOOL_OUTPUT_SCHEMAS = {
|
|
|
192
193
|
},
|
|
193
194
|
walle_memory_status: ANY_OBJECT_SCHEMA,
|
|
194
195
|
walle_live_capabilities: ANY_OBJECT_SCHEMA,
|
|
196
|
+
walle_ctm_context: ANY_OBJECT_SCHEMA,
|
|
197
|
+
walle_ctm_remote_access_status: ANY_OBJECT_SCHEMA,
|
|
195
198
|
walle_search_sessions: ANY_OBJECT_SCHEMA,
|
|
196
199
|
walle_get_session: ANY_OBJECT_SCHEMA,
|
|
197
200
|
walle_context_pack: ANY_OBJECT_SCHEMA,
|
|
@@ -243,6 +246,8 @@ const TOOL_ANNOTATIONS = {
|
|
|
243
246
|
brain_stats: READ_ONLY_TOOL_ANNOTATION,
|
|
244
247
|
walle_memory_status: READ_ONLY_TOOL_ANNOTATION,
|
|
245
248
|
walle_live_capabilities: READ_ONLY_TOOL_ANNOTATION,
|
|
249
|
+
walle_ctm_context: READ_ONLY_TOOL_ANNOTATION,
|
|
250
|
+
walle_ctm_remote_access_status: READ_ONLY_TOOL_ANNOTATION,
|
|
246
251
|
walle_list_sources: READ_ONLY_TOOL_ANNOTATION,
|
|
247
252
|
walle_source_ingest: ADDITIVE_WRITE_TOOL_ANNOTATION,
|
|
248
253
|
walle_search_sessions: READ_ONLY_TOOL_ANNOTATION,
|
|
@@ -280,6 +285,7 @@ const MCP_TOOLS = [
|
|
|
280
285
|
limit: { type: 'number', description: 'Max memories/session snippets/entities per source (default 5, max 20)' },
|
|
281
286
|
include_memories: { type: 'boolean', description: 'Include Wall-E memory search results (default true when route needs Wall-E)' },
|
|
282
287
|
include_sessions: { type: 'boolean', description: 'Include CTM coding-session context (default true for session routes)' },
|
|
288
|
+
include_ctm_operational: { type: 'boolean', description: 'Include CTM operational context such as current phone URLs and Dev Tunnel status (default true for CTM operational routes)' },
|
|
283
289
|
include_entities: { type: 'boolean', description: 'Include knowledge-graph entity matches (default true for people/work routes)' },
|
|
284
290
|
entity_name: { type: 'string', description: 'Optional explicit entity/person/project/tool name to look up' },
|
|
285
291
|
force_memory: { type: 'boolean', description: 'Search Wall-E memory even when routing says live/public/direct' },
|
|
@@ -501,6 +507,33 @@ const MCP_TOOLS = [
|
|
|
501
507
|
properties: {},
|
|
502
508
|
},
|
|
503
509
|
},
|
|
510
|
+
{
|
|
511
|
+
name: 'walle_ctm_context',
|
|
512
|
+
description: 'Resolve CTM operational and session-memory context for CTM primary, mobile phone URLs, Dev Tunnel, /m/, and related CTM session-memory questions. Use this instead of generic memory for CTM remote-access answers.',
|
|
513
|
+
inputSchema: {
|
|
514
|
+
type: 'object',
|
|
515
|
+
properties: {
|
|
516
|
+
query: { type: 'string', description: 'The CTM/mobile/session-memory question to resolve' },
|
|
517
|
+
context: { type: 'string', description: 'Optional nearby conversation context' },
|
|
518
|
+
limit: { type: 'number', description: 'Max CTM session-memory snippets to include (default 5, max 10)' },
|
|
519
|
+
force: { type: 'boolean', description: 'Force CTM operational lookup even if the query classifier is unsure' },
|
|
520
|
+
timeout_ms: { type: 'number', description: 'Timeout for CTM API calls (default 6000)' },
|
|
521
|
+
cooldown_ms: { type: 'number', description: 'Cooldown for CTM API retry suppression (default 0 for this exact lookup)' },
|
|
522
|
+
},
|
|
523
|
+
required: ['query'],
|
|
524
|
+
},
|
|
525
|
+
},
|
|
526
|
+
{
|
|
527
|
+
name: 'walle_ctm_remote_access_status',
|
|
528
|
+
description: 'Read current CTM setup/network status and summarize active phone access URLs, including Microsoft Dev Tunnel and Tailscale. Read-only.',
|
|
529
|
+
inputSchema: {
|
|
530
|
+
type: 'object',
|
|
531
|
+
properties: {
|
|
532
|
+
timeout_ms: { type: 'number', description: 'Timeout for the CTM setup/network API call (default 6000)' },
|
|
533
|
+
cooldown_ms: { type: 'number', description: 'Cooldown for CTM API retry suppression (default 0)' },
|
|
534
|
+
},
|
|
535
|
+
},
|
|
536
|
+
},
|
|
504
537
|
{
|
|
505
538
|
name: 'walle_list_sources',
|
|
506
539
|
description: 'List source adapters Wall-E can ingest, including Claude Code, Codex, Gemini, and Wall-E JSONL sessions.',
|
|
@@ -627,7 +660,10 @@ const MCP_TOOLS = [
|
|
|
627
660
|
description: 'Run a dry integrity scan for brain memory, knowledge, entity, and index consistency.',
|
|
628
661
|
inputSchema: {
|
|
629
662
|
type: 'object',
|
|
630
|
-
properties: {
|
|
663
|
+
properties: {
|
|
664
|
+
limit: { type: 'number', description: 'Max issue rows to return in the sample (default 50, max 500)' },
|
|
665
|
+
include_all: { type: 'boolean', description: 'Return all issue rows instead of a bounded sample' },
|
|
666
|
+
},
|
|
631
667
|
},
|
|
632
668
|
},
|
|
633
669
|
{
|
|
@@ -702,24 +738,47 @@ async function executeTool(name, args) {
|
|
|
702
738
|
until: args.until,
|
|
703
739
|
};
|
|
704
740
|
const hasFilters = Object.values(filters).some(Boolean);
|
|
705
|
-
|
|
706
|
-
//
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
741
|
+
// Person-aware recall: if the query references a person, expand the search to
|
|
742
|
+
// their aliases / email / @handle so messages that reference them indirectly
|
|
743
|
+
// still match (full-name-only search misses email/handle mentions).
|
|
744
|
+
let personTerms;
|
|
745
|
+
let resolvedPerson = '';
|
|
746
|
+
try {
|
|
747
|
+
const inferred = inferEntityName(args.query);
|
|
748
|
+
if (inferred) {
|
|
749
|
+
const ident = brain.resolvePersonIdentities(inferred);
|
|
750
|
+
if (ident && Array.isArray(ident.terms) && ident.terms.length > 1) {
|
|
751
|
+
personTerms = ident.terms;
|
|
752
|
+
resolvedPerson = ident.canonical;
|
|
715
753
|
}
|
|
716
|
-
}
|
|
717
|
-
}
|
|
718
|
-
|
|
719
|
-
|
|
754
|
+
}
|
|
755
|
+
} catch {}
|
|
756
|
+
const memorySearch = await searchWallEMemories({
|
|
757
|
+
query: args.query,
|
|
758
|
+
limit,
|
|
759
|
+
filters,
|
|
760
|
+
hybrid: !hasFilters,
|
|
761
|
+
terms: personTerms,
|
|
762
|
+
});
|
|
763
|
+
const out = {
|
|
764
|
+
results: memorySearch.results.map(formatMemoryResult),
|
|
720
765
|
filters_applied: Object.fromEntries(Object.entries(filters).filter(([, value]) => Boolean(value))),
|
|
721
|
-
vector_search_used:
|
|
766
|
+
vector_search_used: memorySearch.vector_search_used,
|
|
767
|
+
source: memorySearch.source,
|
|
768
|
+
warnings: memorySearch.source.ok ? [] : [memorySearch.source],
|
|
722
769
|
};
|
|
770
|
+
if (resolvedPerson) out.resolved_person = resolvedPerson;
|
|
771
|
+
// Empty stored memory is NOT a dead end — steer the caller to escalate to
|
|
772
|
+
// live sources / the full chat pipeline rather than declining.
|
|
773
|
+
if (memorySearch.source.ok && memorySearch.results.length === 0) {
|
|
774
|
+
out.hint = 'No stored memory matched. The brain may not have ingested this yet — this does NOT mean no history exists.';
|
|
775
|
+
out.next_steps = [
|
|
776
|
+
'Call ask_walle with the original request — it can search LIVE Slack / Gmail / Calendar and compose the reply.',
|
|
777
|
+
...(inferEntityName(args.query) ? ["Call list_people / entity_search to resolve the person's email or @handle, then search those."] : []),
|
|
778
|
+
'If this is a write/compose request, draft it with [placeholders] for any unknowns instead of declining.',
|
|
779
|
+
];
|
|
780
|
+
}
|
|
781
|
+
return out;
|
|
723
782
|
}
|
|
724
783
|
case 'remember': {
|
|
725
784
|
const result = brain.insertKnowledge({
|
|
@@ -821,7 +880,7 @@ async function executeTool(name, args) {
|
|
|
821
880
|
let entityCount = 0, embeddingCount = 0;
|
|
822
881
|
try { entityCount = brain.listEntities({ limit: 1 }).length > 0 ? brain.getDb().prepare('SELECT COUNT(*) as c FROM entities').get().c : 0; } catch {}
|
|
823
882
|
try { embeddingCount = brain.getDb().prepare("SELECT COUNT(*) as c FROM embedding_map").get().c; } catch {}
|
|
824
|
-
return { ...stats, entity_count: entityCount, embedding_count: embeddingCount };
|
|
883
|
+
return { ...stats, entity_count: entityCount, embedding_count: embeddingCount, storage_risk: brain.getStorageRisk?.() || null };
|
|
825
884
|
}
|
|
826
885
|
case 'walle_memory_status': {
|
|
827
886
|
ensureBuiltinSourceAdapters();
|
|
@@ -830,6 +889,7 @@ async function executeTool(name, args) {
|
|
|
830
889
|
return {
|
|
831
890
|
ok: true,
|
|
832
891
|
stats,
|
|
892
|
+
storage_risk: brain.getStorageRisk?.() || null,
|
|
833
893
|
ctm_db: await getCtmDbStatus(),
|
|
834
894
|
resources: {
|
|
835
895
|
static: MCP_RESOURCES.map((resource) => resource.uri),
|
|
@@ -844,6 +904,22 @@ async function executeTool(name, args) {
|
|
|
844
904
|
case 'walle_live_capabilities': {
|
|
845
905
|
return getLiveCapabilities();
|
|
846
906
|
}
|
|
907
|
+
case 'walle_ctm_context': {
|
|
908
|
+
return ctmOperationalContext.lookupCtmOperationalContext(args);
|
|
909
|
+
}
|
|
910
|
+
case 'walle_ctm_remote_access_status': {
|
|
911
|
+
const status = await ctmContextClient.getRemoteAccessStatus({}, {
|
|
912
|
+
timeoutMs: args.timeout_ms || 6000,
|
|
913
|
+
cooldownMs: args.cooldown_ms || 0,
|
|
914
|
+
});
|
|
915
|
+
return {
|
|
916
|
+
ok: !status.reason,
|
|
917
|
+
source: status.source || 'ctm-api',
|
|
918
|
+
reason: status.reason || '',
|
|
919
|
+
api_transport: status.api_transport || null,
|
|
920
|
+
remote_access: status.reason ? null : ctmOperationalContext.summarizeRemoteAccess(status),
|
|
921
|
+
};
|
|
922
|
+
}
|
|
847
923
|
case 'walle_list_sources': {
|
|
848
924
|
ensureBuiltinSourceAdapters();
|
|
849
925
|
return {
|
|
@@ -877,16 +953,21 @@ async function executeTool(name, args) {
|
|
|
877
953
|
const ctmResults = args.prefer_db === false
|
|
878
954
|
? { ok: false, results: [], skipped: true, reason: 'prefer_db_false' }
|
|
879
955
|
: await safeCtmSearchSessions({ query: args.query, limit });
|
|
880
|
-
const
|
|
881
|
-
?
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
956
|
+
const memorySearch = args.include_memory === false
|
|
957
|
+
? {
|
|
958
|
+
results: [],
|
|
959
|
+
source: { searched: false, ok: true, source: 'wall-e-memory', count: 0, reason: '' },
|
|
960
|
+
vector_search_used: false,
|
|
961
|
+
}
|
|
962
|
+
: await searchWallEMemories({ query: args.query, limit: limit * 4, hybrid: false });
|
|
963
|
+
const memoryResults = memorySearch.results
|
|
964
|
+
.filter(isSessionMemory)
|
|
965
|
+
.slice(0, limit * 2)
|
|
966
|
+
.map((memory, index) => ({
|
|
967
|
+
...formatSessionMemory(memory),
|
|
968
|
+
source_layer: 'wall-e-memory',
|
|
969
|
+
rank: 10000 + index,
|
|
970
|
+
}));
|
|
890
971
|
const ctmSourceLayer = ctmResults.source === 'ctm-api' ? 'ctm-api' : 'ctm-db';
|
|
891
972
|
const dbResults = (ctmResults.results || []).map((result, index) => ({
|
|
892
973
|
...result,
|
|
@@ -915,6 +996,10 @@ async function executeTool(name, args) {
|
|
|
915
996
|
},
|
|
916
997
|
wall_e_memory: {
|
|
917
998
|
searched: args.include_memory !== false,
|
|
999
|
+
ok: Boolean(memorySearch.source.ok),
|
|
1000
|
+
source: memorySearch.source.source,
|
|
1001
|
+
reason: memorySearch.source.reason || '',
|
|
1002
|
+
error: memorySearch.source.error || '',
|
|
918
1003
|
count: memoryResults.length,
|
|
919
1004
|
},
|
|
920
1005
|
},
|
|
@@ -997,7 +1082,10 @@ async function executeTool(name, args) {
|
|
|
997
1082
|
}
|
|
998
1083
|
case 'walle_repair_status': {
|
|
999
1084
|
const repair = require('./utils/repair');
|
|
1000
|
-
return repair.scanIntegrity()
|
|
1085
|
+
return compactRepairScan(repair.scanIntegrity(), {
|
|
1086
|
+
limit: args.limit,
|
|
1087
|
+
include_all: args.include_all,
|
|
1088
|
+
});
|
|
1001
1089
|
}
|
|
1002
1090
|
case 'walle_rebuild_ctm_message_index': {
|
|
1003
1091
|
requireWriteConfirmation('walle_rebuild_ctm_message_index', args);
|
|
@@ -1038,6 +1126,19 @@ function routeWallEQuery(query, opts = {}) {
|
|
|
1038
1126
|
const selfProfile = add('self_profile', [/\b(my|me)\b.*\b(writing style|communication style|tone|personality|leadership style|work style)\b/, /\banaly[sz]e my\b/, /\bwhat.*\bpatterns\b.*\bme\b/, /\bam i too\b/]);
|
|
1039
1127
|
const liveAction = add('live_action', [/\bsend\b/, /\bpost\b/, /\bcreate\b/, /\bschedule\b/, /\bopen\b/, /\bdelete\b/, /\bupdate\b/, /\bunread\b/, /\binbox\b/, /\btoday'?s calendar\b/, /\btomorrow'?s calendar\b/]);
|
|
1040
1128
|
const publicCurrent = add('public_current', [/\bweb\b/, /\bpublic\b/, /\bnews\b/, /\blatest\b/, /\bcurrent\b/, /\bprice\b/, /\bstock\b/, /\bweather\b/, /\bdocs?\b/, /\bofficial\b/]);
|
|
1129
|
+
const ctmOperational = ctmOperationalContext.classifyCtmOperationalQuery(query, { context: opts.context });
|
|
1130
|
+
if (ctmOperational.required) {
|
|
1131
|
+
matched.push({ name: 'ctm_operational_context', hits: ctmOperational.matched });
|
|
1132
|
+
return {
|
|
1133
|
+
route: 'ctm_operational_context',
|
|
1134
|
+
should_use_walle: true,
|
|
1135
|
+
primary_tools: ['walle_ctm_context', 'walle_ctm_remote_access_status', 'walle_search_sessions'],
|
|
1136
|
+
secondary_tools: ['walle_lookup_context', 'search_memories'],
|
|
1137
|
+
avoid_until_memory_miss: ['web_search', 'web_fetch'],
|
|
1138
|
+
reason: ctmOperational.reason,
|
|
1139
|
+
matched,
|
|
1140
|
+
};
|
|
1141
|
+
}
|
|
1041
1142
|
|
|
1042
1143
|
if (selfProfile) {
|
|
1043
1144
|
return {
|
|
@@ -1118,7 +1219,9 @@ async function lookupWallEContext(args = {}) {
|
|
|
1118
1219
|
const isProfileLookup = route.matched?.some(match => match.name === 'self_profile');
|
|
1119
1220
|
const includeMemories = args.include_memories === true || (args.include_memories !== false && shouldUseWallE);
|
|
1120
1221
|
const includeSessions = args.include_sessions === true
|
|
1121
|
-
|| (args.include_sessions !== false && (route.route === 'walle_session_context' || isProfileLookup));
|
|
1222
|
+
|| (args.include_sessions !== false && (route.route === 'walle_session_context' || route.route === 'ctm_operational_context' || isProfileLookup));
|
|
1223
|
+
const includeCtmOperational = args.include_ctm_operational === true
|
|
1224
|
+
|| (args.include_ctm_operational !== false && route.route === 'ctm_operational_context');
|
|
1122
1225
|
const includeEntities = args.include_entities === true
|
|
1123
1226
|
|| (args.include_entities !== false && (route.route === 'walle_private_memory' || args.force_memory));
|
|
1124
1227
|
const inferredEntityName = String(args.entity_name || inferEntityName(query) || '').trim();
|
|
@@ -1130,13 +1233,34 @@ async function lookupWallEContext(args = {}) {
|
|
|
1130
1233
|
session_results: [],
|
|
1131
1234
|
entity_results: [],
|
|
1132
1235
|
context_pack: null,
|
|
1236
|
+
ctm_operational_context: null,
|
|
1133
1237
|
sources: {
|
|
1134
1238
|
memories: { searched: false, count: 0 },
|
|
1135
1239
|
ctm_sessions: { searched: false, count: 0 },
|
|
1240
|
+
ctm_operational: { searched: false, count: 0 },
|
|
1136
1241
|
entities: { searched: false, count: 0 },
|
|
1137
1242
|
},
|
|
1138
1243
|
};
|
|
1139
1244
|
|
|
1245
|
+
if (includeCtmOperational) {
|
|
1246
|
+
const operational = await ctmOperationalContext.lookupCtmOperationalContext({
|
|
1247
|
+
query,
|
|
1248
|
+
context: args.context,
|
|
1249
|
+
limit,
|
|
1250
|
+
force: true,
|
|
1251
|
+
});
|
|
1252
|
+
result.ctm_operational_context = operational;
|
|
1253
|
+
result.sources.ctm_operational = {
|
|
1254
|
+
searched: true,
|
|
1255
|
+
ok: Boolean(operational.ok),
|
|
1256
|
+
required: Boolean(operational.required),
|
|
1257
|
+
reason: operational.ok ? '' : 'ctm_operational_context_unavailable',
|
|
1258
|
+
remote_access: operational.sources?.remote_access || null,
|
|
1259
|
+
ctm_sessions: operational.sources?.ctm_sessions || null,
|
|
1260
|
+
count: (operational.session_results || []).length,
|
|
1261
|
+
};
|
|
1262
|
+
}
|
|
1263
|
+
|
|
1140
1264
|
if (includeSessions) {
|
|
1141
1265
|
const sessionQuery = isProfileLookup ? 'thorough review fix issues commit high-agency' : query;
|
|
1142
1266
|
const sessionSearch = await safeCtmSearchSessions({
|
|
@@ -1169,21 +1293,37 @@ async function lookupWallEContext(args = {}) {
|
|
|
1169
1293
|
since: args.since,
|
|
1170
1294
|
until: args.until,
|
|
1171
1295
|
};
|
|
1172
|
-
|
|
1296
|
+
const memorySearch = await searchWallEMemories({
|
|
1297
|
+
query: memoryQuery,
|
|
1298
|
+
limit,
|
|
1299
|
+
filters,
|
|
1300
|
+
hybrid: !Object.values(filters).some(Boolean),
|
|
1301
|
+
});
|
|
1302
|
+
result.memory_results = memorySearch.results.map(formatMemoryResult);
|
|
1173
1303
|
result.sources.memories = {
|
|
1174
1304
|
searched: true,
|
|
1175
1305
|
query: memoryQuery,
|
|
1176
1306
|
filters_applied: Object.fromEntries(Object.entries(filters).filter(([, value]) => Boolean(value))),
|
|
1307
|
+
ok: Boolean(memorySearch.source.ok),
|
|
1308
|
+
source: memorySearch.source.source,
|
|
1309
|
+
reason: memorySearch.source.reason || '',
|
|
1310
|
+
error: memorySearch.source.error || '',
|
|
1311
|
+
vector_search_used: memorySearch.vector_search_used,
|
|
1177
1312
|
count: result.memory_results.length,
|
|
1178
1313
|
};
|
|
1179
1314
|
}
|
|
1180
1315
|
|
|
1181
1316
|
if (includeEntities) {
|
|
1182
1317
|
if (inferredEntityName) {
|
|
1183
|
-
|
|
1318
|
+
const entitySearch = safeSearchEntitiesForContext(inferredEntityName, limit);
|
|
1319
|
+
result.entity_results = entitySearch.results;
|
|
1184
1320
|
result.sources.entities = {
|
|
1185
1321
|
searched: true,
|
|
1186
1322
|
query: inferredEntityName,
|
|
1323
|
+
ok: Boolean(entitySearch.ok),
|
|
1324
|
+
source: entitySearch.source,
|
|
1325
|
+
reason: entitySearch.reason || '',
|
|
1326
|
+
error: entitySearch.error || '',
|
|
1187
1327
|
count: result.entity_results.length,
|
|
1188
1328
|
};
|
|
1189
1329
|
} else {
|
|
@@ -1220,6 +1360,98 @@ function compactSnippet(text, max = 260) {
|
|
|
1220
1360
|
return cleaned.length > max ? cleaned.slice(0, Math.max(0, max - 1)).trimEnd() + '...' : cleaned;
|
|
1221
1361
|
}
|
|
1222
1362
|
|
|
1363
|
+
function classifySourceError(err, fallbackReason = 'source_read_failed') {
|
|
1364
|
+
const code = String(err?.code || '');
|
|
1365
|
+
const message = String(err?.message || err || '');
|
|
1366
|
+
const text = `${code} ${message}`.toLowerCase();
|
|
1367
|
+
let reason = fallbackReason;
|
|
1368
|
+
if (/sqlite_(corrupt|notadb)|database disk image is malformed|malformed database|database schema is corrupt/.test(text)) {
|
|
1369
|
+
reason = 'sqlite_structural_corruption';
|
|
1370
|
+
} else if (/sqlite_(busy|locked)|database is locked|database table is locked/.test(text)) {
|
|
1371
|
+
reason = 'sqlite_locked';
|
|
1372
|
+
} else if (/sqlite_cantopen|unable to open database file/.test(text)) {
|
|
1373
|
+
reason = 'sqlite_unavailable';
|
|
1374
|
+
} else if (/database not initialized/.test(text)) {
|
|
1375
|
+
reason = 'sqlite_not_initialized';
|
|
1376
|
+
}
|
|
1377
|
+
return {
|
|
1378
|
+
ok: false,
|
|
1379
|
+
reason,
|
|
1380
|
+
error: message,
|
|
1381
|
+
code: code || undefined,
|
|
1382
|
+
};
|
|
1383
|
+
}
|
|
1384
|
+
|
|
1385
|
+
function sourceStatus(source, patch = {}) {
|
|
1386
|
+
return {
|
|
1387
|
+
searched: true,
|
|
1388
|
+
ok: true,
|
|
1389
|
+
source,
|
|
1390
|
+
reason: '',
|
|
1391
|
+
error: '',
|
|
1392
|
+
count: 0,
|
|
1393
|
+
...patch,
|
|
1394
|
+
};
|
|
1395
|
+
}
|
|
1396
|
+
|
|
1397
|
+
function safeBrainSearchMemories(args = {}) {
|
|
1398
|
+
try {
|
|
1399
|
+
const results = brain.searchMemories(args);
|
|
1400
|
+
return {
|
|
1401
|
+
results,
|
|
1402
|
+
source: sourceStatus('wall-e-memory', {
|
|
1403
|
+
ok: true,
|
|
1404
|
+
count: results.length,
|
|
1405
|
+
}),
|
|
1406
|
+
};
|
|
1407
|
+
} catch (err) {
|
|
1408
|
+
const failure = classifySourceError(err, 'wall_e_memory_search_failed');
|
|
1409
|
+
return {
|
|
1410
|
+
results: [],
|
|
1411
|
+
source: sourceStatus('wall-e-memory', {
|
|
1412
|
+
...failure,
|
|
1413
|
+
count: 0,
|
|
1414
|
+
}),
|
|
1415
|
+
};
|
|
1416
|
+
}
|
|
1417
|
+
}
|
|
1418
|
+
|
|
1419
|
+
async function searchWallEMemories({ query, limit, filters = {}, hybrid = true, terms } = {}) {
|
|
1420
|
+
const base = safeBrainSearchMemories({ query, limit, terms, ...filters });
|
|
1421
|
+
let results = base.results;
|
|
1422
|
+
let vectorSearchUsed = false;
|
|
1423
|
+
const vectorStatus = { attempted: false, ok: true, reason: '', error: '' };
|
|
1424
|
+
|
|
1425
|
+
if (base.source.ok && hybrid && _embeddings && _embeddings.isAvailable()) {
|
|
1426
|
+
vectorStatus.attempted = true;
|
|
1427
|
+
try {
|
|
1428
|
+
const queryEmb = await _embeddings.computeEmbedding(query);
|
|
1429
|
+
if (queryEmb) {
|
|
1430
|
+
const vectorResults = _embeddings.searchSimilarMemories(queryEmb, limit);
|
|
1431
|
+
if (vectorResults.length > 0) {
|
|
1432
|
+
results = _embeddings.reciprocalRankFusion(results, vectorResults, limit);
|
|
1433
|
+
vectorSearchUsed = true;
|
|
1434
|
+
}
|
|
1435
|
+
}
|
|
1436
|
+
} catch (err) {
|
|
1437
|
+
const failure = classifySourceError(err, 'wall_e_vector_search_failed');
|
|
1438
|
+
vectorStatus.ok = false;
|
|
1439
|
+
vectorStatus.reason = failure.reason;
|
|
1440
|
+
vectorStatus.error = failure.error;
|
|
1441
|
+
}
|
|
1442
|
+
}
|
|
1443
|
+
|
|
1444
|
+
return {
|
|
1445
|
+
results,
|
|
1446
|
+
vector_search_used: vectorSearchUsed,
|
|
1447
|
+
source: sourceStatus('wall-e-memory', {
|
|
1448
|
+
...base.source,
|
|
1449
|
+
count: results.length,
|
|
1450
|
+
vector: vectorStatus,
|
|
1451
|
+
}),
|
|
1452
|
+
};
|
|
1453
|
+
}
|
|
1454
|
+
|
|
1223
1455
|
function evidenceFromMemory(memory, aspect) {
|
|
1224
1456
|
return {
|
|
1225
1457
|
kind: 'memory',
|
|
@@ -1265,17 +1497,20 @@ function profileAspectEvidence(aspect, limit) {
|
|
|
1265
1497
|
|
|
1266
1498
|
for (const query of PROFILE_ASPECT_QUERIES[aspect] || []) {
|
|
1267
1499
|
if (rows.length >= limit) break;
|
|
1268
|
-
|
|
1500
|
+
const memorySearch = safeBrainSearchMemories({ query, limit: Math.max(limit, 4) });
|
|
1501
|
+
for (const memory of memorySearch.results) {
|
|
1269
1502
|
addMemory(memory);
|
|
1270
1503
|
if (rows.length >= limit) break;
|
|
1271
1504
|
}
|
|
1272
1505
|
}
|
|
1273
1506
|
|
|
1274
1507
|
if (aspect === 'preferences') {
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1508
|
+
try {
|
|
1509
|
+
for (const row of brain.findKnowledge({ category: 'preference', status: 'active', limit, orderBy: 'confidence DESC' })) {
|
|
1510
|
+
addKnowledge(row);
|
|
1511
|
+
if (rows.length >= limit) break;
|
|
1512
|
+
}
|
|
1513
|
+
} catch {}
|
|
1279
1514
|
}
|
|
1280
1515
|
|
|
1281
1516
|
return rows.slice(0, limit);
|
|
@@ -1476,6 +1711,7 @@ function buildPostflightCheck(args = {}) {
|
|
|
1476
1711
|
|
|
1477
1712
|
function inferEntityName(query) {
|
|
1478
1713
|
const text = String(query || '').trim();
|
|
1714
|
+
// End-anchored question patterns (case-insensitive): the whole tail is the name.
|
|
1479
1715
|
for (const pattern of [
|
|
1480
1716
|
/\bdo you know\s+(.+?)[?.!]?$/i,
|
|
1481
1717
|
/\bwho is\s+(.+?)[?.!]?$/i,
|
|
@@ -1487,6 +1723,19 @@ function inferEntityName(query) {
|
|
|
1487
1723
|
return match[1].replace(/^["']|["']$/g, '').trim();
|
|
1488
1724
|
}
|
|
1489
1725
|
}
|
|
1726
|
+
// Mid-sentence references to a proper-noun name (1-3 capitalized words), e.g.
|
|
1727
|
+
// "search history about Eric Gu", "write Eric Gu's anniversary note",
|
|
1728
|
+
// "a note for Eric Gu". Case-sensitive so it keys on the capitalized name.
|
|
1729
|
+
const NAME = "([A-Z][\\w.-]*(?:\\s+[A-Z][\\w.-]*){0,2})";
|
|
1730
|
+
for (const pattern of [
|
|
1731
|
+
new RegExp("\\b(?:note|message|email|card|memo)\\s+(?:to|for|about)\\s+" + NAME),
|
|
1732
|
+
new RegExp("\\babout\\s+" + NAME),
|
|
1733
|
+
new RegExp("\\bfor\\s+" + NAME + "(?:'s)?\\b"),
|
|
1734
|
+
new RegExp(NAME + "'s\\b"),
|
|
1735
|
+
]) {
|
|
1736
|
+
const match = text.match(pattern);
|
|
1737
|
+
if (match?.[1]) return match[1].trim();
|
|
1738
|
+
}
|
|
1490
1739
|
return '';
|
|
1491
1740
|
}
|
|
1492
1741
|
|
|
@@ -1512,6 +1761,39 @@ function searchEntitiesForContext(name, limit) {
|
|
|
1512
1761
|
}));
|
|
1513
1762
|
}
|
|
1514
1763
|
|
|
1764
|
+
function safeSearchEntitiesForContext(name, limit) {
|
|
1765
|
+
try {
|
|
1766
|
+
const results = searchEntitiesForContext(name, limit);
|
|
1767
|
+
return {
|
|
1768
|
+
ok: true,
|
|
1769
|
+
source: 'wall-e-entities',
|
|
1770
|
+
results,
|
|
1771
|
+
count: results.length,
|
|
1772
|
+
};
|
|
1773
|
+
} catch (err) {
|
|
1774
|
+
const failure = classifySourceError(err, 'wall_e_entity_search_failed');
|
|
1775
|
+
return {
|
|
1776
|
+
...failure,
|
|
1777
|
+
source: 'wall-e-entities',
|
|
1778
|
+
results: [],
|
|
1779
|
+
count: 0,
|
|
1780
|
+
};
|
|
1781
|
+
}
|
|
1782
|
+
}
|
|
1783
|
+
|
|
1784
|
+
function compactRepairScan(scan = {}, { limit = 50, include_all = false } = {}) {
|
|
1785
|
+
const issues = Array.isArray(scan.issues) ? scan.issues : [];
|
|
1786
|
+
const cap = include_all ? issues.length : clampLimit(limit, 50, 500);
|
|
1787
|
+
const sample = issues.slice(0, cap);
|
|
1788
|
+
return {
|
|
1789
|
+
...scan,
|
|
1790
|
+
issues: sample,
|
|
1791
|
+
issues_sample: sample,
|
|
1792
|
+
issues_truncated: sample.length < issues.length,
|
|
1793
|
+
total_issues: issues.length,
|
|
1794
|
+
};
|
|
1795
|
+
}
|
|
1796
|
+
|
|
1515
1797
|
function clampLimit(value, fallback, max) {
|
|
1516
1798
|
const n = Number(value || fallback);
|
|
1517
1799
|
if (!Number.isFinite(n)) return fallback;
|