Skip to content

Embedding Options

What should I run, on my platform, and what will it cost me? This page answers that question in one read. It is a capability matrix and a set of pointers, not a restatement of the full reference — see Configuration: Embedder sidecar for every flag, environment variable, and resolution-order detail.

liminis-context-graph needs an external embedding backend reachable at startup. It talks to that backend over the OpenAI-compatible POST /v1/embeddings contract, selected with either --embedder-uds <path> (Unix domain socket) or --embedder-http <url> (HTTP).

Capability matrix

OptionPlatform(s)InstallSetup / model costDimensionFlagOffline?Dimension auto-probe?Unreachable at startupVerification
Swift CoreML sidecarmacOS 26+Xcode command-line tools; build from native/local-inference/~500 MB disk for the BGE-base-en-v1.5 CoreML model, downloaded on first setup; no per-call cost768 (fixed, BGE-base-en-v1.5)--embedder-uds (or no flag — auto-detected at /tmp/liminis-inference.sock)Yes, fully localYesFail-fast (socket-service mode) or bounded retry-and-degrade (--mcp-stdio) — see Embedder sidecarVerified — the swift test suite, and verify-embedding-parity.py (cosine parity vs. the PyTorch reference, run manually — not yet wired into CI)
Infinity (Python, sentence-transformers-based)Linux, macOS, WindowsInstall and run Infinity yourself; no download bundled with this repoDepends on the model you load; Infinity itself is free/open-source, no per-call costVaries (model-chosen)--embedder-httpYes, fully localYesFail-fast or retry-and-degrade, same as aboveNot independently verified in this repo — relies on the generic OpenAI-compatible contract. Listed as an unauthenticated-compatible server in Configuration
OllamaLinux, macOS, WindowsInstall Ollama, pull an embedding model (e.g. nomic-embed-text)Model download only (varies by model, typically a few hundred MB); no per-call costVaries (model-chosen)--embedder-httpYes, fully localYesFail-fast or retry-and-degrade, same as aboveNot independently verified in this repo — relies on the generic OpenAI-compatible contract. Listed with a concrete recipe in Configuration: MCP client config recipes
vLLM / text-embeddings-inference (TEI)Linux (GPU recommended); macOS/Windows via DockerInstall vLLM or TEI, load a modelModel download (varies); no per-call cost; GPU strongly recommended for throughputVaries (model-chosen)--embedder-httpYes, fully localYesFail-fast or retry-and-degrade, same as aboveNot independently verified in this repo — relies on the generic OpenAI-compatible contract. Listed in Configuration: MCP client config recipes
Hosted OpenAI-compatible provider (e.g. OpenAI /v1/embeddings)Any (network required)An API key; no local installNo download; per-call pricing set by the providerModel-chosen (e.g. 1536 for text-embedding-3-small)--embedder-http + LCG_EMBEDDING_API_KEY (or OPENAI_API_KEY)No — requires networkYesFail-fast — an auth rejection (401/403) is always fatal and is not bypassable via LCG_EMBEDDING_DIMOpenAI’s own /v1/embeddings is the concrete, verified case — see Configuration: HTTP transport. Other self-described OpenAI-compatible hosted providers are not verified beyond this.

Every non-macOS, non-OpenAI-hosted row above is caveated deliberately: none of them has been run against a live instance and tested end-to-end in this repository. Their rows exist because the wire contract they claim to speak matches what OaiEmbedder sends and expects — not because this repo has executed an integration test against them. Treat that as “should work, matches the documented shape,” not “verified working here.”

Any OpenAI-compatible endpoint is a valid target

The rows above are examples, not an exhaustive list. Any server that accepts POST /v1/embeddings with an OpenAI-shaped {input, model} request and returns an OpenAI-shaped {data: [{embedding}]} response is a valid --embedder-http target. This is the actual extension point — if your preferred embedding server speaks that contract, point --embedder-http at it and it will work, whether or not it’s named above. See ADR 0006 and ADR 0016 for the wire contract itself.

No bundled cross-platform option

If you are on Linux or Windows: there is currently no bundled, zero-setup embedder for your platform. The Swift CoreML sidecar is macOS-only (it depends on CoreML and, for extraction, Apple Foundation Models — neither exists on other platforms). You must run one of the external options above (or any other OpenAI-compatible server) yourself and point liminis-context-graph at it with --embedder-http.

This isn’t an oversight: a native, in-process, cross-platform Rust embedder was evaluated and rejected. See docs/spikes/native-embedder-2026-05.md for the full spike — candle was a NO-GO, ort was GO-with-caveats, and neither was ever built into production. Out-of-process, over the same wire contract as every other row in the matrix above, remains the supported path on every platform.

Switching embedders on an existing workspace is not a drop-in swap

The embedding dimension is fixed into the graph’s LadybugDB schema (FLOAT[dim]) at database-creation time. liminis-context-graph auto-probes the dimension of whatever embedder you configure at startup; LCG_EMBEDDING_DIM can override a probe failure, but it cannot resolve a genuine mismatch between a newly-configured embedder’s dimension and vectors already stored under the old one.

If you switch to a different-dimension embedder against a workspace that already has content in its .lcg/ database, that is not something you can just reconfigure and restart into — see Configuration: Switching an existing workspace’s embedder for the remedy (full re-ingest, or knowledge_recover with rebuild_from_workspace_wal).

Even a same-dimension model swap invalidates stored vectors. Changing the embedding model — even to one that happens to produce the same dimension — means your existing vectors were computed by a different model and are no longer comparable to freshly-embedded ones. Issue #440 added model-identity stamping and mismatch detection for exactly this case (knowledge_status’s embedding_model_status field, and the embeddings_recompute_failed / embeddings_recompute_skipped_no_text counters) — see Operations: knowledge_status health fields for the full mechanics.

Embedding is not extraction

This page is about embedding — the --embedder-uds/--embedder-http flags above. It has nothing to do with extraction, the separate process of turning text into entities and relationships, configured independently via --extractor-uds/--extractor-http/ANTHROPIC_API_KEY. On macOS, the same sidecar process can happen to serve both endpoints (/v1/embeddings for embedding, /v1/chat/completions for extraction), which makes the two easy to conflate — but they are selected, resolved, and can fail independently of each other. See Configuration: Extractor: local or hosted for full extraction configuration guidance.

The macOS socket path is not shared with the Electron app

liminis-context-graph’s own default UDS auto-discovery path is /tmp/liminis-inference.sock — a single, well-known, machine-wide path. The Electron liminis app does not use that path: it launches its own sidecar process bound to a separate, per-workspace socket at <workspaceRoot>/.liminis/local-inference.sock.

These are two different sockets serving two different processes’ sidecars — never one shared socket. A liminis-context-graph binary started by hand does not see, and cannot reach, the sidecar the Electron app started for its own workspace, and vice versa. If you run a manual CLI session alongside the app, expect to start (or point at) your own sidecar rather than assuming the app’s is reachable at the well-known path.

Documents liminis-context-graph v0.16.4.