#3967·LightRAG

_generate_collection_suffix folds distinct model names onto one container name

Author: danielaskddCreated Sep 15, 2026Updated Sep 15, 2026

Summary

BaseVectorStorage._generate_collection_suffix() builds the model-isolation suffix as:

python
safe_model_name = re.sub(r"[^a-zA-Z0-9_]", "_", model_name.lower())
return f"{safe_model_name}_{embedding_dim}d"

Case and every non-alphanumeric character fold to _, so distinct model identities collapse onto one suffix. With a shared dimension they resolve to the same physical container:

model name suffix
vendor/model:v1 vendor_model_v1_1024d
vendor_model/v1 vendor_model_v1_1024d
Vendor/Model:V1 vendor_model_v1_1024d

Two deployments on different models would then share a collection / table / index, and their vectors are not comparable. Slash-and-colon model identifiers are ordinary — Ollama (nomic-embed-text:v1.5), HuggingFace (BAAI/bge-m3), and OpenRouter-style names all take this shape.

Scope

The helper is on BaseVectorStorage and used by Milvus, Qdrant, PostgreSQL and (as of #3966) OpenSearch. Any fix belongs here rather than in one backend: the value of the helper is that one embedding configuration resolves to the same name everywhere, so a per-backend digest would trade this collision for a worse inconsistency.

Found by

Codex review on #3966. That PR takes the narrower step available to one backend — OpenSearch records the original model_name in the index _meta and compares it when attaching, so a folding collision is refused with an actionable error instead of silently sharing vectors. That is a refusal, not co-existence: the two models still map to one index name.

Sketch, not a decision

Appending a short digest of the original identity (e.g. the first 8 hex of a SHA-256 over the raw model_name) makes folding-equivalent names distinct while keeping the readable prefix — vendor_model_v1_1024d_3f2a9c11. The migration question that comes with it is the real work: every existing suffixed container was named under the current rule, so changing the rule renames all of them, across four backends, each with its own legacy-detection path. Worth designing before implementing.

Generated with Claude Code