Typed config for the collection bounded context, resolved via
hive-di defconfig. Reads [:milvus :collections] block from
~/.config/hive-mcp/config.edn.
Two fields:
:sunset — set of Milvus collection names that are RETIRED.
Locator returns them in known-collections (so reads
still fan out to legacy data) but excludes from
active-collections (so writes never land there).:base-collection-name — Chroma form of the legacy 768-d
collection. Default "hive-mcp-memory" mirrors
hive-milvus.collection.naming/legacy-base-collection.Typed config for the collection bounded context, resolved via
hive-di `defconfig`. Reads `[:milvus :collections]` block from
`~/.config/hive-mcp/config.edn`.
Two fields:
- `:sunset` — set of Milvus collection names that are RETIRED.
Locator returns them in `known-collections` (so reads
still fan out to legacy data) but excludes from
`active-collections` (so writes never land there).
- `:base-collection-name` — Chroma form of the legacy 768-d
collection. Default `"hive-mcp-memory"` mirrors
`hive-milvus.collection.naming/legacy-base-collection`.L3 — ICollectionEnsure impl. Idempotent collection creation with
dim-check.
Wraps the imperative hive-milvus.store.index/ensure-collection!
in the Result railway and adds an in-process dim-registry that
rejects re-ensures requesting a different dimension for the same
collection name, surfacing a dim mismatch at ensure! time rather
than at the first failing upsert.
L3 — `ICollectionEnsure` impl. Idempotent collection creation with dim-check. Wraps the imperative `hive-milvus.store.index/ensure-collection!` in the Result railway and adds an in-process dim-registry that rejects re-ensures requesting a different dimension for the same collection name, surfacing a dim mismatch at `ensure!` time rather than at the first failing upsert.
THE DIMENSION INVARIANT: the width of the vector the embedder produces for a collection MUST equal the width that collection holds.
When it does not, nothing crashes. Milvus rejects an insert with error 1804, which a write path can swallow; and a SEARCH with a wrong-width query vector either errors or — the dangerous case, when another model happens to share the width — returns confident neighbours from a space the query was never embedded into. That is noise wearing the costume of an answer, and it is the shape the 2026-07-12 outage wore.
hive-milvus.store.search.boundary/CollectionEmbedder and
hive-milvus.embedder/embed-for-entry already REFUSE to serve on a mismatch
(:embedder/dim-mismatch) — read path and write path. That is the per-call
half of the invariant, and it is the half that keeps a wrong vector out of
the index.
This namespace is the OTHER half: assert it ONCE, at startup, so a misconfiguration is discovered when the server boots rather than on the first query of the day, silently, per call, forever.
Pure core / effectful shell:
check — pure, one collection.
violations — pure, a set of already-read (collection, expected, actual).
verify — the boundary: reads live embedder dims, calls the pure core.
UNKNOWN IS NOT OK. naming/dim-of returns nil for a collection whose width
is not knowable from its name (anything that is not a memory collection).
Those are reported under :unknown — never folded into :ok. A checker
that reports 'fine' when it means 'I could not tell' is the exact failure
this file exists to prevent.
THE DIMENSION INVARIANT: the width of the vector the embedder produces for a collection MUST equal the width that collection holds. When it does not, nothing crashes. Milvus rejects an insert with error 1804, which a write path can swallow; and a SEARCH with a wrong-width query vector either errors or — the dangerous case, when another model happens to share the width — returns confident neighbours from a space the query was never embedded into. That is noise wearing the costume of an answer, and it is the shape the 2026-07-12 outage wore. `hive-milvus.store.search.boundary/CollectionEmbedder` and `hive-milvus.embedder/embed-for-entry` already REFUSE to serve on a mismatch (`:embedder/dim-mismatch`) — read path and write path. That is the per-call half of the invariant, and it is the half that keeps a wrong vector out of the index. This namespace is the OTHER half: assert it ONCE, at startup, so a misconfiguration is discovered when the server boots rather than on the first query of the day, silently, per call, forever. Pure core / effectful shell: `check` — pure, one collection. `violations` — pure, a set of already-read (collection, expected, actual). `verify` — the boundary: reads live embedder dims, calls the pure core. UNKNOWN IS NOT OK. `naming/dim-of` returns nil for a collection whose width is not knowable from its name (anything that is not a memory collection). Those are reported under `:unknown` — never folded into `:ok`. A checker that reports 'fine' when it means 'I could not tell' is the exact failure this file exists to prevent.
L2 — default ICollectionLocator impl.
Thin wrapper composing the pure naming layer (naming/ref-for-dim)
with the sunset-aware config (config/sunset?). Like the router,
reads config lazily on each call so hot-flips propagate.
The locator is the single source of truth for the
spec→CollectionRef mapping. The write pipeline must NEVER
construct a CollectionRef from a raw type or string — only from a
resolved ProviderSpec via this protocol. That invariant is what
eliminates the bypass paths that fed the 1804 bug.
L2 — default `ICollectionLocator` impl. Thin wrapper composing the pure naming layer (`naming/ref-for-dim`) with the sunset-aware config (`config/sunset?`). Like the router, reads config lazily on each call so hot-flips propagate. The locator is the single source of truth for the spec→`CollectionRef` mapping. The write pipeline must NEVER construct a CollectionRef from a raw type or string — only from a resolved `ProviderSpec` via this protocol. That invariant is what eliminates the bypass paths that fed the 1804 bug.
L1 pure — collection-name derivation.
Two pure functions:
chroma-name : dim → Chroma collection name.
768 stays on the legacy hive-mcp-memory; other
dims get the -<dim>d suffix.milvus-name : Chroma name → Milvus name (underscores not
hyphens). Idempotent — a name already in Milvus
form passes through. Reuses
hive-milvus.collections/collection->milvus-name
so the two definitions cannot drift.Why this lives outside routing.clj: SRP. Routing is about
resolving a ProviderSpec; naming is about projecting a dim to a
string. The L2 locator composes both.
L1 pure — collection-name derivation.
Two pure functions:
- `chroma-name` : dim → Chroma collection name.
768 stays on the legacy `hive-mcp-memory`; other
dims get the `-<dim>d` suffix.
- `milvus-name` : Chroma name → Milvus name (underscores not
hyphens). Idempotent — a name already in Milvus
form passes through. Reuses
`hive-milvus.collections/collection->milvus-name`
so the two definitions cannot drift.
Why this lives outside `routing.clj`: SRP. Routing is about
resolving a `ProviderSpec`; naming is about projecting a dim to a
string. The L2 locator composes both.L0 contract — collection bounded context.
Two narrow protocols (ISP):
ICollectionLocator — spec → CollectionRef. Pure lookup. Knows
sunset state so writes can avoid retired
collections while reads can fan out across
both active + sunset (graceful drain).ICollectionEnsure — create-if-missing on the backend with
mandatory dim-check. Rejects an ensure!
whose ref-dim disagrees with an existing
collection's dim — the precise check that
prevents the silent 1804 schema-mismatch.Reload-safety: defonce-guarded.
L0 contract — collection bounded context.
Two narrow protocols (ISP):
- `ICollectionLocator` — spec → `CollectionRef`. Pure lookup. Knows
sunset state so writes can avoid retired
collections while reads can fan out across
both active + sunset (graceful drain).
- `ICollectionEnsure` — create-if-missing on the backend with
mandatory dim-check. Rejects an `ensure!`
whose ref-dim disagrees with an existing
collection's dim — the precise check that
prevents the silent 1804 schema-mismatch.
Reload-safety: `defonce`-guarded.Multi-collection helpers: filtering, naming.
Multi-collection helpers: filtering, naming.
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |