fix: resolve search, database, and docker bugs (#2079)

* fix: resolve search, database, and docker bugs (#1913, #1916, #1956, #1957, #2048)

- Fix concept/concepts param mismatch in SearchManager.normalizeParams (#1916)
- Add FTS5 keyword fallback when ChromaDB is unavailable (#1913, #2048)
- Add periodic WAL checkpoint and journal_size_limit to prevent unbounded WAL growth (#1956)
- Add periodic clearFailed() to purge stale pending_messages (#1957)
- Fix nounset-safe TTY_ARGS expansion in docker/claude-mem/run.sh

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: prevent silent data loss on non-XML responses, add queue info to /health (#1867, #1874)

- ResponseProcessor: mark messages as failed (with retry) instead of confirming
  when the LLM returns non-XML garbage (auth errors, rate limits) (#1874)
- Health endpoint: include activeSessions count for queue liveness monitoring (#1867)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: cache isFts5Available() at construction time

Addresses Greptile review: avoid DDL probe (CREATE + DROP) on every text
query. Result is now cached in _fts5Available at construction.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Alex Newman
2026-04-19 22:19:18 -07:00
committed by GitHub
parent 8b6e61c70b
commit be99a5d690
11 changed files with 423 additions and 267 deletions
+26
View File
@@ -557,6 +557,32 @@ export class WorkerService {
logger.error('WORKER', 'Stale session reaper error with non-Error', {}, new Error(String(e)));
}
}
// Purge failed pending messages to prevent unbounded queue growth (#1957)
try {
const pendingStore = this.sessionManager.getPendingMessageStore();
const purged = pendingStore.clearFailed();
if (purged > 0) {
logger.info('SYSTEM', `Purged ${purged} failed pending messages`);
}
} catch (e) {
if (e instanceof Error) {
logger.error('WORKER', 'Failed message purge error', {}, e);
} else {
logger.error('WORKER', 'Failed message purge error with non-Error', {}, new Error(String(e)));
}
}
// Periodic WAL checkpoint to prevent unbounded WAL growth (#1956)
try {
this.dbManager.getSessionStore().db.run('PRAGMA wal_checkpoint(PASSIVE)');
} catch (e) {
if (e instanceof Error) {
logger.error('WORKER', 'WAL checkpoint error', {}, e);
} else {
logger.error('WORKER', 'WAL checkpoint error with non-Error', {}, new Error(String(e)));
}
}
}, 2 * 60 * 1000);
// Auto-recover orphaned queues (fire-and-forget with error logging)