diff --git a/gitnexus/src/core/search/hybrid-search.ts b/gitnexus/src/core/search/hybrid-search.ts index b049ea79e8..b76a9f5e91 100644 --- a/gitnexus/src/core/search/hybrid-search.ts +++ b/gitnexus/src/core/search/hybrid-search.ts @@ -113,12 +113,13 @@ export const mergeWithRRF = ( }; /** - * Check if hybrid search is available - * LadybugDB FTS is always available once the database is initialized. - * Semantic search is optional - hybrid works with just FTS if embeddings aren't ready. + * Check if hybrid search is available. + * FTS indexes may be missing on read-only MCP connections (see #1403); + * callers should inspect `ftsAvailable` from searchFTSFromLbug for + * per-query availability. This helper is a coarse gate only. */ export const isHybridSearchReady = (): boolean => { - return true; // FTS is always available via LadybugDB when DB is open + return true; // FTS is attempted on every query; ftsAvailable signals actual availability }; /** diff --git a/gitnexus/src/mcp/local/local-backend.ts b/gitnexus/src/mcp/local/local-backend.ts index 343ca639bf..6175af875e 100644 --- a/gitnexus/src/mcp/local/local-backend.ts +++ b/gitnexus/src/mcp/local/local-backend.ts @@ -979,7 +979,7 @@ export class LocalBackend { timing, ...(!ftsUsed && { warning: - 'FTS extension unavailable - keyword search degraded. Run: gitnexus analyze --force to rebuild indexes.', + 'FTS indexes missing — keyword search degraded. Run: gitnexus analyze --force to rebuild indexes.', }), }; } diff --git a/gitnexus/src/server/api.ts b/gitnexus/src/server/api.ts index a7ca95f5c7..27000813ab 100644 --- a/gitnexus/src/server/api.ts +++ b/gitnexus/src/server/api.ts @@ -1077,6 +1077,8 @@ export const createServer = async (port: number, host: string = '127.0.0.1') => sources: ['semantic'], })); } else if (mode === 'bm25') { + // TODO(#1403): propagate ftsAvailable to API response so server + // users get the same "indexes missing" warning as MCP/CLI callers. searchResults = (await searchFTSFromLbug(query, limit)).results; searchResults = searchResults.map((r: any, i: number) => ({ ...r, @@ -1091,6 +1093,7 @@ export const createServer = async (port: number, host: string = '127.0.0.1') => await import('../core/embeddings/embedding-pipeline.js'); searchResults = await hybridSearch(query, limit, executeQuery, semSearch); } else { + // TODO(#1403): propagate ftsAvailable to API response (see bm25 branch above). searchResults = (await searchFTSFromLbug(query, limit)).results; } }