fix(memory): accept local default model path migration#92954
Conversation
|
Codex review: needs maintainer review before merge. Reviewed June 14, 2026, 11:22 AM ET / 15:22 UTC. Summary PR surface: Source +72, Tests +100. Total +172 across 3 files. Reproducibility: no. high-confidence current-main live reproduction was run in this read-only review. Source inspection makes the failure path high-confidence because current main and v2026.6.6 exact-match Review metrics: 1 noteworthy metric.
Stored data model Merge readiness Overall follows the weaker of proof and patch quality, so missing proof can cap an otherwise strong patch. Rank-up moves:
Risk before merge
Maintainer options:
Next step before merge
Security Review detailsBest possible solution: Land this focused compatibility rule only if maintainers accept the default-model equivalence contract, and keep #92808 open for the broader install, CLI, and post-upgrade concerns. Do we have a high-confidence way to reproduce the issue? No high-confidence current-main live reproduction was run in this read-only review. Source inspection makes the failure path high-confidence because current main and v2026.6.6 exact-match Is this the best way to solve the issue? Yes for the focused identity slice: the comparator is the path that pauses status/search on model identity mismatch, and the PR keeps non-local, non-default, providerKey, vector dims, source, scope, chunking, and tokenizer checks strict. The remaining question is maintainer acceptance of the upgrade contract, not a different code location. AGENTS.md: found and applied where relevant. Codex review notes: model internal, reasoning high; reviewed against 3826cda4d854. Label changesLabel changes:
Label justifications:
Evidence reviewedPR surface: Source +72, Tests +100. Total +172 across 3 files. View PR surface stats
What I checked:
Likely related people:
What the crustacean ranks mean
Shiny media proof means a screenshot, video, or linked artifact directly shows the changed behavior. Runtime, network, CSP, and security claims still need visible diagnostics. How this review workflow works
|
vincentkoc
left a comment
There was a problem hiding this comment.
Deep review found a merge blocker in extensions/memory-core/src/memory/manager-reindex-state.ts:51: basename-only compatibility treats any local file named like the default GGUF as the official default model. A different model with that filename can suppress reindexing and mix incompatible embedding spaces.
Best fix: bind identity compatibility to the canonical resolved model artifact/source, not the basename. The provider identity needs a durable artifact identity seam before this is safe to merge.
Treat the official local default embedding model's hf URI and downloaded GGUF path identities as equivalent so upgraded local memory indexes do not pause solely on path-format changes.
Avoid filtered array tail access in the local model filename helper while preserving the same compatibility behavior.
251d26e to
696a28f
Compare
vincentkoc
left a comment
There was a problem hiding this comment.
Maintainer repair complete. Exact provider-owned aliases preserve both HF-to-path and path-to-HF indexes without making arbitrary paths equivalent. Focused tests, typechecks, lint/format, Plugin SDK baseline check, and fresh branch autoreview are clean.
|
Maintainer closeout proof:
Proof gap: no live native model download/load run; full Testbox check:changed was unavailable because the Blacksmith CLI is not installed in this environment. |
* fix(memory): accept local default model path migration Treat the official local default embedding model's hf URI and downloaded GGUF path identities as equivalent so upgraded local memory indexes do not pause solely on path-format changes. * fix(memory): satisfy local identity lint Avoid filtered array tail access in the local model filename helper while preserving the same compatibility behavior. * fix(memory): preserve local embedding identity aliases --------- Co-authored-by: Vincent Koc <[email protected]>
* fix(memory): accept local default model path migration Treat the official local default embedding model's hf URI and downloaded GGUF path identities as equivalent so upgraded local memory indexes do not pause solely on path-format changes. * fix(memory): satisfy local identity lint Avoid filtered array tail access in the local model filename helper while preserving the same compatibility behavior. * fix(memory): preserve local embedding identity aliases --------- Co-authored-by: Vincent Koc <[email protected]>
* fix(memory): accept local default model path migration Treat the official local default embedding model's hf URI and downloaded GGUF path identities as equivalent so upgraded local memory indexes do not pause solely on path-format changes. * fix(memory): satisfy local identity lint Avoid filtered array tail access in the local model filename helper while preserving the same compatibility behavior. * fix(memory): preserve local embedding identity aliases --------- Co-authored-by: Vincent Koc <[email protected]>
* fix(memory): accept local default model path migration Treat the official local default embedding model's hf URI and downloaded GGUF path identities as equivalent so upgraded local memory indexes do not pause solely on path-format changes. * fix(memory): satisfy local identity lint Avoid filtered array tail access in the local model filename helper while preserving the same compatibility behavior. * fix(memory): preserve local embedding identity aliases --------- Co-authored-by: Vincent Koc <[email protected]>
Summary
hf:GGUF model identity were treated as mismatched when the upgraded local provider reported the same downloaded GGUF by filesystem path.hf:URI and downloaded GGUF path formats, including the corresponding legacy providerKey hash.Real behavior proof
hf:ggml-org/embeddinggemma-300m-qat-q8_0-GGUF/embeddinggemma-300m-qat-Q8_0.ggufidentity remains valid when the current local provider reports the downloadedembeddinggemma-300m-qat-Q8_0.gguffilesystem path, while a different GGUF path still mismatches./media/vdc/code/ai/aispace/openclaw-worktrees/issue-92808, branchfeat/issue-92808.mkdir -p /media/vdc/code/ai/aispace/openclaw-issue-92808-evidence/models && curl -L --fail --retry 2 --connect-timeout 30 --max-time 600 -o /media/vdc/code/ai/aispace/openclaw-issue-92808-evidence/models/embeddinggemma-300m-qat-Q8_0.gguf https://huggingface.co/ggml-org/embeddinggemma-300m-qat-q8_0-GGUF/resolve/main/embeddinggemma-300m-qat-Q8_0.ggufmemory_index_meta_v1to the legacy defaulthf:URI identity/providerKey, then reopens the production manager with the local GGUF path and verifies status/search/sync.{ "proof": "local-provider-default-model-upgrade-status-search", "head": "251d26eec66a9e64962feab2c72a9700e24e7865", "runtime": "node --import tsx; production memory manager; registered llama.cpp local provider; real GGUF; real SQLite; no Vitest", "model": { "defaultHfUri": "hf:ggml-org/embeddinggemma-300m-qat-q8_0-GGUF/embeddinggemma-300m-qat-Q8_0.gguf", "localPath": "/media/vdc/code/ai/aispace/openclaw-issue-92808-evidence/models/embeddinggemma-300m-qat-Q8_0.gguf", "fileName": "embeddinggemma-300m-qat-Q8_0.gguf", "sizeBytes": 328577056 }, "providerKeys": { "legacyHfUriProviderKey": "a65bf29e73a7aa6d94f94c77377b9d4e17a2298505ddb598523262bdc77ac89b", "expectedLocalPathProviderKey": "fbb45b98bdc118c6f23d91a9dfa4f836f3f188d2884900c1e790a5c50908a6d2", "keysDiffer": true }, "buildWithLocalPath": { "syncElapsedMs": 4076, "statusIdentity": "valid", "dirty": false, "chunks": 1, "metaProvider": "local", "metaModel": "/media/vdc/code/ai/aispace/openclaw-issue-92808-evidence/models/embeddinggemma-300m-qat-Q8_0.gguf", "metaVectorDims": 768 }, "legacyRewrite": { "beforeModel": "/media/vdc/code/ai/aispace/openclaw-issue-92808-evidence/models/embeddinggemma-300m-qat-Q8_0.gguf", "afterModel": "hf:ggml-org/embeddinggemma-300m-qat-q8_0-GGUF/embeddinggemma-300m-qat-Q8_0.gguf", "afterProviderKeyMatchesLegacyHfUri": true }, "verifyAfterUpgrade": { "statusBeforeSearch": { "identity": "valid", "dirty": true, "chunks": 1 }, "searchElapsedMs": 3981, "searchHits": 1, "firstHitPath": "MEMORY.md", "statusAfterSearch": { "identity": "valid", "dirty": true, "chunks": 1 } }, "postUpgradeSync": { "syncElapsedMs": 4, "statusAfterSync": { "identity": "valid", "dirty": false, "chunks": 1 }, "metaModelAfterSync": "hf:ggml-org/embeddinggemma-300m-qat-q8_0-GGUF/embeddinggemma-300m-qat-Q8_0.gguf", "metaProviderKeyAfterSync": "a65bf29e73a7aa6d94f94c77377b9d4e17a2298505ddb598523262bdc77ac89b" }, "acceptedLegacyDefaultIdentity": true }vectorDims: 768), the legacyhf:URI providerKey and current filesystem-path providerKey were different, and the reopened manager still reportedindexIdentity: valid. A realmanager.search()returned oneMEMORY.mdhit before post-upgrade sync, and the follow-up sync settled status tovalid/dirty=falsewithout rebuilding from a mismatched/paused state. Unrelated model/provider changes remain mismatched in regression coverage.openclaw memory index --force, or desktop app proof was run. The added proof does exercise the native llama.cpp provider with the official default GGUF, production memory manager status/search/sync, and real SQLite files; broader install/CLI/plugin concerns from [Bug]: Title: Local embedding provider breaks on upgrade (two consecutive releases) — no migration path, misleading error #92808 remain outside this focused PR scope.Regression Test Plan
extensions/memory-core/src/memory/manager-reindex-state.test.tsandextensions/memory-core/src/memory/index.test.ts.DEFAULT_LOCAL_MODELremains valid/searchable when reopened with a filesystem path ending in the same official default GGUF filename; a different GGUF path remains mismatched.Merge risk
local, the shared officialDEFAULT_LOCAL_MODEL, a non-hf:filesystem-style path with the same default GGUF filename, and the expected legacy providerKey hashes.Refs #92808rather than a closing reference because it does not claim to resolve every install/CLI/plugin concern.Root Cause
hf:URI when no explicit path is set, but after upgrade/config repair the same downloaded GGUF can be reported as a filesystem path.resolveMemoryIndexIdentityStatecomparedmeta.modelandproviderKeyas exact strings, so the same official default model identity was treated as a provider/model change.DEFAULT_LOCAL_MODEL, the storedmemory_index_meta_v1, and the existing providerKey hash remain the source of truth; the comparator only treats the old and new serialized identity forms as equivalent for this one official local default model.