Summary
Hermes's SQLite session store (hermes_state.py) refuses to open at all when the underlying Python's sqlite3 module wasn't compiled with FTS5 support. This affects common Python installations (e.g. Python 3.11 on macOS built via Homebrew on certain formulae, some pyenv builds). The error message is Error: Could not open session database: no such module: fts5. When this fires, all SQLite-backed features silently break (session history, hermes sessions list, hermes insights, any GUI companion like Scarf that reads state.db) while the user's primary flow still works due to the JSONL fallback.
Environment
- Hermes version: v0.10.0 (2026.4.16)
- Platform: macOS Darwin 25.2.0, ARM64 (M-series)
- Python used by venv: 3.11.13 (lacks FTS5)
- Python alternatives on same machine that DO have FTS5: 3.12.9, 3.13.7, 3.14.3 (all Homebrew)
- schema_version in state.db: 6
Reproduction
# Confirm the Python can't do FTS5
/path/to/hermes/venv/bin/python -c "import sqlite3; sqlite3.connect(':memory:').execute('CREATE VIRTUAL TABLE t USING fts5(x)')"
# sqlite3.OperationalError: no such module: fts5
# Now run hermes sessions list
hermes sessions list
# Error: Could not open session database: no such module: fts5
# All .jsonl session files exist on disk in hermes/sessions/,
# but state.db's sessions/messages tables stay empty.
Impact
hermes sessions list returns error — user can't see session history.
hermes insights is non-functional (depends on state.db).
- External tools that read state.db (e.g. Scarf macOS GUI companion) show empty views — hard to diagnose for users because Hermes's own core flow (WhatsApp/CLI chat) keeps working via JSONL fallback, so users think Hermes is working fine.
- Warning in gateway.log:
SQLite session store unavailable, falling back to JSONL: no such module: fts5 — correctly logged but easy to miss among other startup messages.
Root cause
hermes_state.py attempts to CREATE VIRTUAL TABLE ... USING fts5(...) unconditionally during DB init. When the sqlite3 compile doesn't include the FTS5 module, this statement raises OperationalError: no such module: fts5, preventing the entire DB from being opened.
Suggested fix — three reasonable approaches
Option A (preferred): Detect FTS5 at startup, degrade gracefully
def _has_fts5() -> bool:
try:
conn = sqlite3.connect(':memory:')
conn.execute("CREATE VIRTUAL TABLE _t USING fts5(x)")
conn.close()
return True
except sqlite3.OperationalError:
return False
# In hermes_state.py init:
if _has_fts5():
# create the fts5 virtual tables for session search
...
else:
# log a warning, skip FTS5 search features, but still init session/messages tables
log.warning("FTS5 unavailable; session-text search disabled. Session metadata still tracked.")
...
This keeps session/messages tables functional (so Scarf and hermes sessions list work), just without FTS5-backed search. Users upgrade their Python when convenient.
Option B: Prefer apsw when available (ships with FTS5-enabled SQLite)
try:
import apsw
# use apsw-backed connection; its SQLite always has FTS5
except ImportError:
import sqlite3
# fall through to the Option A graceful-degrade path
Option C: Document the dependency clearly
Add a preflight check in hermes doctor that confirms FTS5 availability and surfaces a remediation hint ("Rebuild venv with Python 3.12+ or install apsw").
Happy to PR
I can submit a PR implementing Option A if that's the preferred direction. It preserves backward compatibility, fixes the silent-break behavior, and doesn't add runtime dependencies.
Related
Similar graceful-degrade pattern already exists in the gateway logs output: the JSONL fallback IS engaged when state.db fails. The fix here just extends the same pattern to keep the DB opened for the non-FTS5 tables rather than refusing entirely.
Summary
Hermes's SQLite session store (
hermes_state.py) refuses to open at all when the underlying Python'ssqlite3module wasn't compiled with FTS5 support. This affects common Python installations (e.g. Python 3.11 on macOS built via Homebrew on certain formulae, some pyenv builds). The error message isError: Could not open session database: no such module: fts5. When this fires, all SQLite-backed features silently break (session history,hermes sessions list,hermes insights, any GUI companion like Scarf that readsstate.db) while the user's primary flow still works due to the JSONL fallback.Environment
Reproduction
Impact
hermes sessions listreturns error — user can't see session history.hermes insightsis non-functional (depends on state.db).SQLite session store unavailable, falling back to JSONL: no such module: fts5— correctly logged but easy to miss among other startup messages.Root cause
hermes_state.pyattempts toCREATE VIRTUAL TABLE ... USING fts5(...)unconditionally during DB init. When the sqlite3 compile doesn't include the FTS5 module, this statement raisesOperationalError: no such module: fts5, preventing the entire DB from being opened.Suggested fix — three reasonable approaches
Option A (preferred): Detect FTS5 at startup, degrade gracefully
This keeps session/messages tables functional (so Scarf and
hermes sessions listwork), just without FTS5-backed search. Users upgrade their Python when convenient.Option B: Prefer
apswwhen available (ships with FTS5-enabled SQLite)Option C: Document the dependency clearly
Add a preflight check in
hermes doctorthat confirms FTS5 availability and surfaces a remediation hint ("Rebuild venv with Python 3.12+ or installapsw").Happy to PR
I can submit a PR implementing Option A if that's the preferred direction. It preserves backward compatibility, fixes the silent-break behavior, and doesn't add runtime dependencies.
Related
Similar graceful-degrade pattern already exists in the gateway logs output: the JSONL fallback IS engaged when state.db fails. The fix here just extends the same pattern to keep the DB opened for the non-FTS5 tables rather than refusing entirely.