-
v6.7.1
StableSome checks failedSecurity Scans / Bandit SAST (pull_request) Successful in 22sSecurity Scans / Dependency Audit (mcp_server) (pull_request) Successful in 1m5sSecurity Scans / Dependency Audit (rss_worker) (pull_request) Successful in 28sSecurity Scans / Test Coverage (pull_request) Failing after 1m32sSecurity Scans / Secret Scan (pull_request) Successful in 5sSecurity Scans / Dependency Audit (web_ui) (pull_request) Successful in 26sDocker Build & Push / Build mcp_server (push) Successful in 15m20sDocker Build & Push / Build web_ui (push) Successful in 5m58sDocker Build & Push / Build rss_worker (push) Successful in 6m48sreleased this
2026-09-15 07:59:27 +00:00 | 2 commits to v6.7.x since this releaseThe 6.6 and 6.7 lines in one release: projects that say what kind of work they hold, memories that say where they came from and whether they can be shared, an embedding backend that's three times faster with no PyTorch in sight, and a recall that stops padding its answers with noise. This release rolls up 6.6.0 through 6.7.1.
A third of the latency, a third of the image (6.7.0)
Embeddings now run on ONNX Runtime instead of sentence-transformers on PyTorch. Same model (all-MiniLM-L6-v2), same vectors: cosine 1.0000 on every sampled text and an identical top-10 on every benchmark query, so nothing you've stored needs re-embedding and no threshold moves.
Measured on arm64 with a 400-memory corpus and 44 queries:
6.6.2 (PyTorch) 6.7.0 (ONNX) Model load 7.8 s 0.8 s Peak memory 924 MB 301 MB embed()p5022.3 ms 7.9 ms remember()p5025 ms 11 ms recall()p5035 ms 23 ms MCP server image 2.04 GB 634 MB PyTorch isn't installed in any image any more. If you need the old path,
EMBEDDING_BACKEND=torchplusrequirements-torch.txtbrings it back. The default model is pinned to a known commit so an upstream re-export can't shift vectors under a live store,EMBEDDING_MODELaccepts a local directory for air-gapped hosts, and the benchmark behind these numbers ships asscripts/embedding_bench.pyso you can check any other model or quantised graph the same way.Recall stops padding (6.7.1)
recall()used to filltop_kwith whatever was left, so two good matches came back with three unrelated memories attached, all headed straight into an agent's context. There's now a relevance floor (RECALL_MIN_SCORE, 0.15), andtop_kis a ceiling: fewer results, or none, is a normal answer.The floor is deliberately low. On the real embedder, correct and incorrect matches overlap between roughly 0.19 and 0.24, and the 0.4 cut first proposed dropped two of eight correct answers. So rather than hide that band, results between the floor and
RECALL_WEAK_SCORE(0.35) come back flaggedweak_match: true, and the agent instructions say to read those but not build on them. The floor gates raw similarity, not the adjusted score, so extracted facts and abandoned experiences that are scored down on purpose still come back when they genuinely match.find_skills()gets its own floor (SKILL_MIN_SCORE, 0.25) and ahigh/lowconfidence on each result. Before,find_skills("python")on a store with no Python skill cheerfully returned a preferences skill, and a skill loads whole.Also fixed in 6.7.1:
- Phantom index entries (#28): an index row whose record had gone could reach recall as an empty result taking a
top_kslot. It's skipped now, and index drift is logged at startup and surfaced inbriefing()instead of only inhealth(), which is how 762 orphans built up unnoticed reindex()covers all five namespaces (#29):preferenceandskillwere missing from the docs, andmemory_audit()silently skipped preferences on an unscoped run- Full
held_backrule text (#32): the list you choose what tobless()from was cut at 80 characters, mid-word - The stale list stopped nagging about your best memories (#34): memories compiled into a skill stop getting touched because the skill carries them, so they were being flagged as stale. They're exempt now
compile_skill()explains an empty compile (#33): when every candidate in a domain comes from one project, it says so and points atbless()or a narrower domain rather than suggesting you lower the gate
Where a memory came from, and whether you can share it (6.6.1, 6.6.2)
Every memory now carries two new fields.
licencerecords redistribution rights:own,open,restrictedorunknown. It's decided at write time. The RSS worker stamps each article from its feed's newlicence:declaration in feeds.yml (ogl-3.0,cc-by-4.0and friends resolve to a class and keep the identifier as a note), andRSS_REQUIRE_LICENCE=truerefuses undeclared feeds outright. When recall returns something stillunknown, alicence_noticeasks you to classify it while it's in front of you, andset_licence(feed_name="...", licence="...")does a whole feed in one call.provenancerecords who's speaking:asserted(you said it),concluded(the system's own reasoning or write-up) orretrieved(an external source). Without it, an inference from last month gets recalled and read as independent evidence for the reasoning that produced it.set_provenance(..., "asserted")is how you vouch for a memory.Both are indexed, returned on every read surface, editable in the web UI, and inherited by extracted facts. Neither changes ranking: landing a field and changing what recall does with it are separate releases, so any future benchmark move can be attributed. Licence is about redistribution rights, not who can see a memory; that's a different axis and a later release.
Projects declare their kind of work (6.6.0)
A project context can now list work-type domains (
python,docker,wcag-accessibility), andrecall(query, domain_filter="python")searches every Python project at once. That reaches the lessons that never cleared a skill's reinforcement gate, which used to need an unfiltered search of everything. Domains use the same vocabulary as compiled skills, so the two can't drift apart.compile_project_domains()suggests them from your stack and recurring tags, with the evidence for each, and the projects page filters on them.Fixed: index migration never worked (6.6.0)
_migrate_indexes()has failed silently on every upgrade since it was written. valkey-py'sdropindex()sends a trailing empty argument that valkey-search rejects, and the error was swallowed by the handler for "index doesn't exist". Any field added to an index in a past release, the knowledge namespace'sprojecttag among them, was only searchable on fresh installs. It now issues the raw command, logs real failures, and the test fake raises the same error the server does so this can't pass the suite again.Upgrading
- The first start rebuilds indexes. Between the migration fix and the two new fields, most instances will drop and recreate their indexes on first boot. It's data-safe: only the index goes, and valkey-search re-indexes the existing records itself. Recall can be incomplete for a short while as that happens, and the startup drift check expects this and stays quiet
- Backfills run once. Episodic, project and preference memories become
licence=own; RSS articles and untraceable knowledge becomeunknown. Provenance lands asretrievedfor articles,assertedfor preferences and project context, andconcludedfor everything else, every episodic memory included. That last one is deliberately conservative, not a judgement on the work - First start downloads an 86 MB ONNX file into a new shared
hf_cachevolume. Air-gapped hosts need to fetch it online first or pointEMBEDDING_MODELat a local directory: a cache filled by the old torch backend doesn't contain it - Building from source? The RSS worker image now builds from the repo root (
-f rss_worker/Dockerfile), like the web UI. The bundled compose files already do this; a hand-rolled one needs the same change and thehf_cachevolume - Expect shorter recall results. That's the floor doing its job.
RECALL_MIN_SCORE=0andSKILL_MIN_SCORE=0restore the old behaviour if you need it
The suite is up to 1913 tests, with
memory/andtools/at 100% line coverage, and the index, backfill and tag-filter paths verified against a real valkey-search rather than only the fakes.Self-hosted, open source, runs on Docker Compose. Python 3.12, FastMCP, Valkey.
Full detail in CHANGELOG.md.
Downloads
-
Source code (ZIP)
0 downloads
-
Source code (TAR.GZ)
0 downloads
- Phantom index entries (#28): an index row whose record had gone could reach recall as an empty result taking a
-
v6.5.1
StableAll checks were successfulDocker Build & Push / Build mcp_server (push) Successful in 18m8sDocker Build & Push / Build rss_worker (push) Successful in 15sSecurity Scans / Dependency Audit (rss_worker) (push) Successful in 30sSecurity Scans / Dependency Audit (web_ui) (push) Successful in 27sSecurity Scans / Dependency Audit (mcp_server) (push) Successful in 1m37sDocker Build & Push / Build web_ui (push) Successful in 31m1sSecurity Scans / Bandit SAST (push) Successful in 7sSecurity Scans / Test Coverage (push) Successful in 1m29sSecurity Scans / Secret Scan (push) Successful in 4sreleased this
2026-07-24 16:07:18 +00:00 | 20 commits to main since this releaseThe 6.5 line lands on main: RSS feeds can now steer your compiled skills, skill bundles carry their feeds with them, and every web UI page fits its viewport down to phone width. This release rolls up 6.5.0 and 6.5.1.
RSS feeds influence compiled skills (6.5.0)
A feed can now be tied to one or more skill domains with an influence score from 1 to 10 — set per feed in the web UI's feed editor (with a suggestion list of existing skill domains) or as a
skills:mapping in feeds.yml. When such a skill is recompiled, the latest articles from its influencing feeds are pulled into a new Feed watch section automatically, no per-article blessing required: the score is how many of its most recent articles a feed contributes, so a 10 dominates the section and a 1 adds a single headline, with the whole section capped bySKILL_FEED_MAX_ARTICLES(default 25, 0 disables).The write gate is untouched — feed items only land through a proposed-and-accepted compile, the section is labelled as unvetted current signal, and feed-item churn is classified low-risk in the change summary so article rotation never drowns out real rule edits. Feeds without an association keep the existing behaviour: their articles never touch a skill unless a human promotes one, and a feed can't bootstrap a skill from nothing — a domain with no experience and no promoted references still compiles nothing from feed association alone. The config mirrors into Valkey (
meta:feed:influence) on every web UI feed save and on each worker ingest cycle, so hand edits to feeds.yml converge too.Skill bundles carry their feeds (6.5.0)
Exporting a skill now includes the RSS feeds that influence its domain — name, URL, topics, mode, project label, and the influence score — as a checksummed
feeds.jsonin the bundle. That's export format version 2, with version 1 bundles still importable. Import previews the feed plan alongside the memory plan and stays strictly additive: a feed missing from the receiving reading list is added (renamed with an "(imported)" suffix if its name is taken by a different URL), a feed already present at most gains the influence entry it lacked, and nothing existing is ever rewritten.No page scrolls sideways any more (6.5.1)
- The RSS feeds table fits on an iPad again: the new Skills column made it six columns wide, so the widths are rebalanced, long skill mappings wrap inside their cell instead of forcing the table wider, and the action buttons flow inline instead of spilling out of a collapsed flex cell.
- A headless audit of all 21 web UI pages at 390, 768, 1024, and 1400px — seeded with long URLs and long content — found horizontal overflow on ten of them from four distinct causes, all fixed. The small-screen
table-layout:autooverrides are gone, the content column gotmin-width:0so a long unbroken URL can't widen the page, headers wrap so action buttons drop below the title, and the three tables that had no width rules got fixed layouts of their own.
Also
- Full test coverage for feed influence, transfer v2, the web routes, and worker sync.
- codeberg.org/ric_harvey links migrated to code.squarecows.com/ric across the README, docs, and CLAUDE.md.
Self-hosted, open source, runs on Docker Compose. Python 3.12, FastMCP, Valkey.
Full detail in CHANGELOG.md.
Downloads
-
Source code (ZIP)
6 downloads
-
Source code (TAR.GZ)
10 downloads
-
v6.4.2 Stable
released this
2026-07-19 23:26:07 +00:00 | 36 commits to main since this releaseThe 6.4 line lands on main: skills that travel between instances, skills that propose themselves, and a test suite that now covers 99.9% of the codebase. This release rolls up 6.4.0 through 6.4.2.
Skills move between instances (6.4.0)
Every skill on the web UI gains an Export button that downloads the skill together with all the source memories it was compiled from as a single zip bundle — self-describing, with a format version and a sha256 checksum for every file, the skill as both JSON and human-readable SKILL.md, and one JSON file per source memory. An Import Skill button takes such a bundle into another OmniMem instance: validated end to end, previewed before anything is written, and strictly additive — existing skills and memories are never overwritten, so replaying a bundle is a no-op. Embeddings never travel; everything is re-embedded on the receiving instance.
Skills propose themselves (6.4.1)
At most once a day, a
briefing()runs an auto skill scan across all projects. Domains with no compiled skill whose lessons already clear the reinforcement gate get a draft proposed automatically — by default only when a rule spans two or more projects, the strongest signal a lesson deserves to become policy. Skills whose sources have changed get a fresh draft compiled so the diff is ready to review. The scan only ever creates proposal stashes, so the propose-and-accept gate is untouched and a human still commits every draft. Ignoring a draft declines it: the identical draft is never raised twice, and it only comes back when the underlying lessons change. Tunables:SKILL_SCAN_INTERVAL_HOURS,SKILL_SCAN_CROSS_PROJECT,SKILL_SCAN_MIN_POOL,SKILL_SCAN_MAX_PROPOSALS.Test coverage rose from 90% to 99.9% (6.4.1)
The suite grew from 1032 to 1291 tests and every application module now sits at 100% line coverage, including code that had never been imported by a test at all: the MCP server entry point (Host/Origin allowlist derivation, the fail-closed public-bind check), the on-connect instructions, and the RSS worker's scheduler. The pass also caught tests that were passing while asserting nothing; all now assert unconditionally and are deterministic regardless of Python's hash seed.
Web UI fixes (6.4.2)
- The articles page shows which feed each article came from instead of a project column that said the same thing on every row
- Articles list in the order they arrived (
created_at), so startup migrations no longer shuffle them - The compiled skills table stays inside the page: long domain names wrap at their hyphens, badges stay in their columns, and the action buttons stack instead of pushing past the edge on narrow viewports
Also fixed
- One corrupt
updated_attimestamp no longer takes down the whole /memories page install.shno longer hangs undercurl | bash, and shows numbered step-by-step progress- Security scans run clean: bandit false positives on deliberate
0.0.0.0test fixtures and a gitleaks false positive (the "key" in "valkey") are suppressed with targeted annotations
Self-hosted, open source, runs on Docker Compose. Python 3.12, FastMCP, Valkey.
Full detail in CHANGELOG.md.
Downloads
-
Source code (ZIP)
11 downloads
-
Source code (TAR.GZ)
12 downloads
-
V6.3.2
Stablereleased this
2026-07-17 15:05:44 +00:00 | 50 commits to main since this releaseAdded
- Five platform deployment guides: step-by-step setup for macOS (Docker Desktop, Apple Silicon and Intel), Raspberry Pi (64-bit OS, native arm64), AWS EC2 (Linux), GCP Compute Engine (Linux), and any Linux server with Tailscale Funnel for a public HTTPS endpoint without a domain or port forwarding. All linked from the README's documentation table and the docs index
- Skill demo playbook:
scripts/skill_demo_playbook.mdwalks a self-contained demo of the skill compiler — fictional moo-reports memories in, reinforcement gate visibly excluding a one-off lesson, propose-and-accept compile, a report written under the skill, knowledge watch flagging a contradicting article, and full cleanup. The seeded wordings and thresholds are verified against a live server (lesson texts cluster at 0.80; the watch trigger clears the 0.35 discovery-similarity floor)
Changed
- The README became a front door and the manual moved to
docs/: the README had grown to over 600 lines of everything at once. It now reads like the omnimem.org landing page — the problem, what OmniMem remembers, what makes it different, a quick start, and links out for the rest — while the detail moved into nine focused pages underdocs/: quick start, features in depth, the skill compiler, the MCP tool reference, the configuration reference, RSS and knowledge, remote access (reverse proxy, OAuth, the 421/403 troubleshooting guide), the web UI tour, and architecture. A newdocs/README.mdindexes the lot, including the existing memory type specs and connection guides - The architecture diagram is Mermaid now: the ASCII box drawing gave way to a rendered Mermaid diagram in both the README and
docs/architecture.md, which also gains a Mermaid recall-pipeline flowchart; the memory lifecycle indocs/features.mdpicked up a state diagram to match. Forgejo renders all three natively - README front-door polish: the omnimem.org link sits directly under the title, the Codeberg notice moved below the badges in small print (and is repeated in the contributing section), a get-going-quickly installer one-liner appears above the fold in a tip callout, the per-namespace memory specs are linked from the documentation section, and the long-obsolete SSE deprecation warning is gone
CI
- Security scans and Docker builds moved to the self-hosted sqcows runner; Python 3.12 is provisioned via uv (setup-python cannot install interpreters on Debian runners)
Downloads
-
Source code (ZIP)
15 downloads
-
Source code (TAR.GZ)
15 downloads
-
v6.1.0 Pre-release
released this
2026-07-10 22:15:38 +00:00 | 50 commits to v6 since this releaseFirst release of the v6 line: the skill compiler (6.0.0) plus the web UI to browse and manage it (6.1.0). The idea in one line — a memory error is noise, ranked and diluted by recall; a skill error is policy, because the agent obeys it. So skills are compiled from your raw memories behind a propose-and-accept gate, never written silently.
The skill compiler (v6.0.0)
Turns distilled domain procedure — drawn from experience and graveyard memories — into loadable
SKILL.mddocuments an agent can pick up to work the way you work in a domain (python, rust, technical-blogging, ...). A skill earns its keep on greenfield projects where no project context exists yet and the skill is the only thing carrying your conventions.- Four new MCP tools:
compile_skill(propose returns a unified diff plus a risk-classified change summary; write commits only that reviewed draft — there is no silent-commit path),find_skills(ranked discovery over name/description/domain, with hand-authored skills outranking generated ones on the same domain),get_skill(returns the whole body intact — skills are never chunked), andbless(promotes a single strong lesson past the reinforcement gate) - Promotion gating: a single episode is a memory; a pattern across episodes earns a rule. Breakthroughs become Do rules, gotchas become Watch rules, graveyard entries become Don't rules, each citing its source memories
- Deterministic compilation: the same sources render the same body, so recompile diffs show substance, not noise. The description (the load trigger) is human-owned and pinned across recompiles
- Briefing integration:
briefing()suggests relevant skills (never auto-loads) and flags when a skill's source memories have changed since compile, with prominence scaled to risk
The web UI rework (v6.1.0)
- Skills section: a catalogue (name, domain, description, state, compile time, load count, pending-proposal banner) and a detail view rendering the rule manifest with reinforcement counts, the full SKILL.md body, and the source manifest linking back to every memory the skill was compiled from. Deliberately read-only — skills only change through the compile gate, so the pages point you at the raw memories instead of offering edit or delete
- Dashboard: the projects card now counts distinct projects by state (active / deprioritised / archived) rather than raw records, a new skills card shows compiled skills and pending proposals, compiled skills join the recent activity feed, and card titles link through to their sections
- Regrouped sidebar: Memory (memories, projects, preferences, experience, graveyard), Skills, Management (duplicates, contradictions, suppressions), Knowledge Management (articles, RSS feeds), and System Management (telemetry, backups)
- Telemetry and metrics: skill loads now surface on
/telemetry(via the shared recall counters) and/metricsgainsnamespace="skill"and the previously missingnamespace="preference"series
Self-hosted, open source, runs on Docker Compose. Python 3.12, FastMCP, Valkey.
Full detail in CHANGELOG.md.
Downloads
-
Source code (ZIP)
8 downloads
-
Source code (TAR.GZ)
11 downloads
- Four new MCP tools:
-
v5.5.3 Stable
released this
2026-07-09 17:58:28 +00:00 | 113 commits to main since this releaseIf you're coming from the 3.x line, this is a big jump. v5 has been run hard internally for months before shipping. This release page collects the headline changes since v3 alongside the v5.5.3 fixes.
Fixed in v5.5.3
- bandit
B324High-severity failure in the security pipeline:_cache_key()inmcp_server/memory/query_expansion.pyusedhashlib.sha1()to fingerprint a query into a cache key, which bandit flags as a weak hash for security. The digest carries no security property (it's only a cache key), so the call now passesusedforsecurity=False, the idiomatic fix that clears the finding without a blanket# nosec
Also in the 5.5.x line
- v5.5.2: OAuth refresh raised
AttributeError→ 500 under FastMCP 3.x. The newer MCP SDK readsrefresh_token.expires_at, but_StoredTokenonly storedcreated_at+expires_in, so every refresh 500d and desktop/claude.ai clients couldn't get a token._StoredTokennow exposesexpires_atas a computed property - v5.5.1: OAuth / MCP access behind a reverse proxy or tunnel (Traefik, Caddy, Tailscale funnel) broke after the FastMCP 3.x upgrade. Its
HostOriginGuardMiddleware421d on unlisted hosts and 403d on scheme-mismatched origins.server.pynow derives the allowed host and fullscheme://host[:port]origin fromOAUTH_BASE_URL/MCP_PUBLIC_URL, withMCP_ALLOWED_HOSTS/MCP_ALLOWED_ORIGINSfor extras
Highlights since v3
Connect claude.ai from the browser (v4.0.0)
A full OAuth 2.1 authorisation server, so claude.ai connects to your self-hosted OmniMem as a connector with no local proxy. Dynamic client registration, PKCE, token refresh with rotation, and a browser login page. Token state persists in Valkey (with AOF) so sessions survive restarts. The 5.5.x fixes above harden this path for real-world proxy/tunnel deployments.
Smarter recall (v5.0.0)
- Fact extraction at ingest: Claude Haiku pulls atomic facts from raw input before storing
- New
preferencenamespace for prescriptive rules ("always update the changelog after a feature") - Temporal-aware retrieval: date-shaped queries get a scoring boost against a memory's
event_date - Query expansion: alternative phrasings unioned at recall time
remember_document()with turn-pair chunking took zero-recall on long transcripts from 45% down to 0%
Faster (v5.2.0, v5.3.0)
- Non-blocking ingest via a background enrichment queue (~0.25s to store and return)
- Recall, dedup and maintenance reuse embeddings already stored in Valkey instead of recomputing them
- Project and state filters are pushed into the vector search so candidate slots stay in-scope
- Projected batch fetches (
get_fields_multi) halve round trips on the scan-heavy hot paths
Security pass (v5.3.0)
- Constant-time bearer token comparison (
hmac.compare_digest) - Fail closed: the server refuses to start unauthenticated on a non-loopback address, and Compose refuses an empty
VALKEY_PASSWORD - Path-traversal hardening on all web UI backup operations
- Denial-of-service caps on uploads (100 MB) and RSS page fetches (
RSS_MAX_PAGE_BYTES) - Per-IP brute-force protection on OAuth login
Self-hosted, open source, runs on Docker Compose. Python 3.12, FastMCP, Valkey.
Full detail in CHANGELOG.md.
Downloads
-
Source code (ZIP)
10 downloads
-
Source code (TAR.GZ)
6 downloads
- bandit
-
v3.13.1 Stable
released this
2026-04-03 16:24:44 +00:00 | 149 commits to main since this releaseFixed
- Restored memories not searchable until manual intervention (#10):
restore_from_filenow automatically re-embeds all restoredmem:*keys after writing them back to Valkey. Previously, backups excluded binary vector data (required bydecode_responses=True), so restored memories had no embeddings and were invisible torecallandrecall_index. The restore response now includes are_embeddedcount restore_allreturn type extended: Now returns(restored_count, skipped_count, restored_keys)so callers know exactly which keys were written- 2 new tests for the dump-restore-recall round-trip and selective re-embedding (462 total)
Removed
- CVE-2026-4539
--ignore-vulnworkaround: Upstream pygments has patched the ReDoS vulnerability in AdlLexer. Removed the--ignore-vuln CVE-2026-4539flag from the pip-audit CI step
Downloads
-
Source code (ZIP)
7 downloads
-
Source code (TAR.GZ)
9 downloads
- Restored memories not searchable until manual intervention (#10):
-
v3.13.0 Stable
released this
2026-03-31 15:37:20 +00:00 | 150 commits to main since this releaseWhat's new
RSS knowledge expiry and new tools
expires_aton RSS knowledge articles: Ingested articles now auto-archive afterMAX_KNOWLEDGE_AGE_DAYS(default 30) during maintenance. Manually stored knowledge is never affectedrecent_knowledge()tool: Query recent articles with filters for days, feed name, topics, and limit. Sorted newest firstpromote_knowledge()tool: Clear an article's expiry to keep it permanently- Phase 3 in auto-maintenance: Expired RSS knowledge items archived automatically alongside dedup and contradiction scans
- 22 new tests (458 total)
Community contribution from @timstoop (PR #9, resolves #6)
Also included since v3.10.2
- Real tool call telemetry via FastMCP middleware (v3.11.0)
- Token overhead page with measured usage since uptime (v3.11.1)
- Performance optimisations (v3.12.0): briefing 3 scans to 1, dashboard/memories single-pass, metrics 60s cache, Docker multi-stage builds, maintenance comparison cap, dedup max_sim during union-find
- Contradiction scanner fix (v3.12.1): similarity gate (>= 0.5) before negation check, results capped at 10
- Version update tooltip fix (v3.10.4, #5)
- Button ordering fix (v3.11.1, #8)
Downloads
-
Source code (ZIP)
8 downloads
-
Source code (TAR.GZ)
9 downloads
-
v3.12.1 Stable
released this
2026-03-30 11:59:51 +00:00 | 156 commits to main since this releaseWhat's new
Performance optimisations (v3.12.0)
- Briefing: 3 episodic scans consolidated into 1 — stale memories, contradiction warnings, and reinstate candidates collected in a single pass. Reduces session-start latency by ~200-400ms per 1,000 memories
- Dashboard: single-pass scan — state counts and recent memories in one loop per namespace instead of two
- Memories page: projects extracted during same scan — removed separate re-scan of all namespaces
- Metrics endpoint: 60-second cache —
/metricsno longer re-scans all memories on every Prometheus scrape. Configurable viaMETRICS_CACHE_TTL - Docker: multi-stage builds — all three Dockerfiles use a builder stage with gcc/g++ and slim runtime with only libgomp1/libopenblas0. Removes ~300-500MB from final images
- Maintenance: pairwise comparison cap — capped at 2,000 comparisons (was unbounded O(n^2))
- Dedup: max_similarity tracked during union-find — eliminates redundant re-scan
- RSS worker: configurable connection pool —
VALKEY_MAX_CONNECTIONSenv var (default 50)
Bug fix (v3.12.1)
- Auto-maintenance contradiction scanner producing mass false positives: The heuristic negation check was running on all pairwise combinations without semantic similarity filtering. Memories containing common words like "use", "with", or "works" matched against almost everything, producing 100+ false positives per briefing. Now embeds content and requires cosine similarity >= 0.5 before checking negation patterns, matching the Tier 1 approach used in
remember(). Results capped at 10 per maintenance run
Also included (v3.11.0–v3.11.1)
- Real tool call telemetry via FastMCP middleware — records call count, duration, response size per tool to Valkey
- Token overhead page shows measured averages from actual usage since uptime
- Prometheus gauges for
omnimem_tool_calls_totalandomnimem_tool_errors_total - Token Overhead link moved after Refresh button on Telemetry page (#8)
Downloads
-
Source code (ZIP)
7 downloads
-
Source code (TAR.GZ)
8 downloads
-
v3.10.4 Stable
released this
2026-03-30 10:40:23 +00:00 | 162 commits to main since this releaseWhat's new
Added
- Token overhead estimation page: New
/token-overheadendpoint in the web UI showing estimated token cost of running OmniMem per Claude Code session. Breaks down static overhead (MCP instructions, tool schemas, deferred tool names) and dynamic per-session overhead (briefing, recall, remember, warn_if_abandoned, update_project_state calls). Includes memory store metrics and project filtering - Sidebar link: "Token Overhead" added to the web UI sidebar under Telemetry
- Configurable overhead constants:
OMNIMEM_INSTRUCTIONS_CHARSandOMNIMEM_TOOL_SCHEMAS_CHARSenv vars allow tuning static overhead estimates - 14 new tests for token overhead estimation (overall coverage now 91%, 431 tests)
Fixed
- Version update tooltip clipped by sidebar (#5): Hover tooltip showing available version was partially hidden due to sidebar overflow clipping. Changed tooltip alignment from centred to right-anchored so it stays within the sidebar bounds
Downloads
-
Source code (ZIP)
5 downloads
-
Source code (TAR.GZ)
8 downloads
- Token overhead estimation page: New