@massa-ai/core 1.14.0 → 1.16.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (37) hide show
  1. package/dist/services/search/contextual-search-rlm.d.ts +35 -14
  2. package/dist/services/search/contextual-search-rlm.d.ts.map +1 -1
  3. package/dist/services/search/contextual-search-rlm.js +274 -53
  4. package/dist/services/search/contextual-search-rlm.js.map +1 -1
  5. package/dist/services/search/graph-stream.d.ts +36 -0
  6. package/dist/services/search/graph-stream.d.ts.map +1 -0
  7. package/dist/services/search/{rlm-synapse.js → graph-stream.js} +11 -90
  8. package/dist/services/search/graph-stream.js.map +1 -0
  9. package/dist/services/search/hybrid-search.d.ts +101 -0
  10. package/dist/services/search/hybrid-search.d.ts.map +1 -0
  11. package/dist/services/search/{rlm-search.js → hybrid-search.js} +89 -46
  12. package/dist/services/search/hybrid-search.js.map +1 -0
  13. package/dist/services/search/index-admin.d.ts +130 -0
  14. package/dist/services/search/index-admin.d.ts.map +1 -0
  15. package/dist/services/search/{rlm-admin.js → index-admin.js} +34 -18
  16. package/dist/services/search/index-admin.js.map +1 -0
  17. package/dist/services/search/project-indexer.d.ts +159 -0
  18. package/dist/services/search/project-indexer.d.ts.map +1 -0
  19. package/dist/services/search/{rlm-indexing.js → project-indexer.js} +51 -79
  20. package/dist/services/search/project-indexer.js.map +1 -0
  21. package/dist/services/search/session-bias.d.ts +41 -0
  22. package/dist/services/search/session-bias.d.ts.map +1 -0
  23. package/dist/services/search/session-bias.js +76 -0
  24. package/dist/services/search/session-bias.js.map +1 -0
  25. package/package.json +2 -2
  26. package/dist/services/search/rlm-admin.d.ts +0 -22
  27. package/dist/services/search/rlm-admin.d.ts.map +0 -1
  28. package/dist/services/search/rlm-admin.js.map +0 -1
  29. package/dist/services/search/rlm-indexing.d.ts +0 -71
  30. package/dist/services/search/rlm-indexing.d.ts.map +0 -1
  31. package/dist/services/search/rlm-indexing.js.map +0 -1
  32. package/dist/services/search/rlm-search.d.ts +0 -27
  33. package/dist/services/search/rlm-search.d.ts.map +0 -1
  34. package/dist/services/search/rlm-search.js.map +0 -1
  35. package/dist/services/search/rlm-synapse.d.ts +0 -44
  36. package/dist/services/search/rlm-synapse.d.ts.map +0 -1
  37. package/dist/services/search/rlm-synapse.js.map +0 -1
@@ -0,0 +1,36 @@
1
+ /**
2
+ * graph-stream — the graph-neighbor RRF stream.
3
+ *
4
+ * PR-B capability module (design.md §4.1). Takes no dependency record at all:
5
+ * it never read a single facade member. Its previous signature accepted the
6
+ * facade as a deliberately-unused `_rlm` purely to match M14's delegate shape,
7
+ * and dropping that parameter is what makes this an extraction rather than a
8
+ * rename — the file has never heard of ContextualSearchRLM, so it contributes
9
+ * nothing to the root's foreign reach (G-HUB, design.md §3.4).
10
+ *
11
+ * Behavior is byte-preserved from rlm-synapse.ts: the body moved verbatim.
12
+ */
13
+ import { SearchResult } from "@massa-ai/shared";
14
+ import type { SearchDegradationReporter } from "./search-diagnostics.js";
15
+ /**
16
+ * Phase 7c: build the graph-neighbor RRF stream. BFS depth-2 over outgoing
17
+ * memory-graph edges; resolved to SearchResults via the memory repository at
18
+ * a fixed sub-hit score (0.45).
19
+ *
20
+ * Id-bridge fix (A3): graph edges connect MEMORY ids, but vector/code-search
21
+ * results key on chunk ids (e.g. "projectId:path:0"). Seeding BFS with chunk
22
+ * ids therefore silently omitted the stream for code queries — the primary
23
+ * use case. We now bridge the two id spaces: collect graph seeds by (a)
24
+ * trying the raw hit ids (preserves the original behavior for memory search
25
+ * where memory ids already flow in), AND (b) mapping each code chunk to
26
+ * memory ids that reference the same filePath/symbol via fullTextSearch.
27
+ * This makes the graph stream participate for code queries while remaining
28
+ * a silent-omit no-op when no bridged seeds resolve.
29
+ *
30
+ * Degradation (silent-omit): returns [] when the neighbor set is empty, the
31
+ * graph store throws, or the memory repo returns nothing. The caller only
32
+ * appends the stream when non-empty, so `resultSets.length` (and thus the
33
+ * `search:reranked` streamCount) always reflects the real stream count.
34
+ */
35
+ export declare function buildGraphStream(resultSets: SearchResult[][], maxResults: number, projectId?: string, reportDegradation?: SearchDegradationReporter): Promise<SearchResult[]>;
36
+ //# sourceMappingURL=graph-stream.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"graph-stream.d.ts","sourceRoot":"","sources":["../../../src/services/search/graph-stream.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,EAAE,YAAY,EAAU,MAAM,kBAAkB,CAAC;AAGxD,OAAO,KAAK,EAAE,yBAAyB,EAAE,MAAM,yBAAyB,CAAC;AAEzE;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAsB,gBAAgB,CACpC,UAAU,EAAE,YAAY,EAAE,EAAE,EAC5B,UAAU,EAAE,MAAM,EAClB,SAAS,CAAC,EAAE,MAAM,EAClB,iBAAiB,CAAC,EAAE,yBAAyB,GAC5C,OAAO,CAAC,YAAY,EAAE,CAAC,CAqHzB"}
@@ -1,97 +1,18 @@
1
1
  /**
2
- * rlm-synapse — Synapse session + graph-stream delegates for ContextualSearchRLM.
2
+ * graph-stream — the graph-neighbor RRF stream.
3
3
  *
4
- * Extracted (M14 Phase 3, T3.2) from contextual-search-rlm.ts. Behavior is
5
- * byte-preserved: bodies moved verbatim with `this` → `rlm`.
4
+ * PR-B capability module (design.md §4.1). Takes no dependency record at all:
5
+ * it never read a single facade member. Its previous signature accepted the
6
+ * facade as a deliberately-unused `_rlm` purely to match M14's delegate shape,
7
+ * and dropping that parameter is what makes this an extraction rather than a
8
+ * rename — the file has never heard of ContextualSearchRLM, so it contributes
9
+ * nothing to the root's foreign reach (G-HUB, design.md §3.4).
10
+ *
11
+ * Behavior is byte-preserved from rlm-synapse.ts: the body moved verbatim.
6
12
  */
7
13
  import { logger } from "@massa-ai/shared";
8
14
  import { getMemoryRepository } from "../../data/memory/memory-repository-factory.js";
9
15
  import { getGraphStore } from "../graph/graph-store-factory.js";
10
- import { getSessionRegistry } from "../synapse/session/index.js";
11
- import { getSynapseManager } from "../synapse/index.js";
12
- import { extractQueryTerms } from "./lexical-search.js";
13
- /**
14
- * Apply session state after the session-independent base result is cached.
15
- * Invalid and workspace-mismatched sessions return the exact base array.
16
- */
17
- export async function applySynapseStateImpl(rlm, baseResults, query, projectId, sessionId, reportDegradation) {
18
- if (!sessionId)
19
- return baseResults;
20
- const registry = rlm.injectedDeps?.sessionRegistry ?? getSessionRegistry();
21
- let session;
22
- try {
23
- session = await registry.getAsync(sessionId);
24
- }
25
- catch (error) {
26
- reportDegradation?.("SYNAPSE_UNAVAILABLE", "synapse_session_lookup");
27
- logger.warn("Synapse session lookup failed — using stateless search", {
28
- sessionId,
29
- projectId,
30
- error: error.message,
31
- });
32
- return baseResults;
33
- }
34
- if (!session || (session.workspaceId && session.workspaceId !== projectId)) {
35
- return baseResults;
36
- }
37
- const synapseManager = rlm.injectedDeps?.synapseManager ?? getSynapseManager();
38
- const allowBufferInjection = session.workspaceId === projectId;
39
- let processed;
40
- try {
41
- processed = synapseManager.process(baseResults, query, {
42
- session,
43
- projectId,
44
- allowBufferInjection,
45
- });
46
- }
47
- catch (error) {
48
- reportDegradation?.("SYNAPSE_UNAVAILABLE", "synapse_processing");
49
- logger.warn("Synapse processing failed — using stateless search", {
50
- sessionId,
51
- projectId,
52
- error: error.message,
53
- });
54
- return baseResults;
55
- }
56
- const baseIds = new Set(baseResults.map((result) => result.id));
57
- return processed.results.filter((result) => {
58
- if (baseIds.has(result.id))
59
- return true;
60
- const metadata = result.metadata;
61
- return allowBufferInjection && metadata?.projectId === projectId;
62
- });
63
- }
64
- /**
65
- * Fuzzy-correct each non-stopword query term via the keyword store's
66
- * vocabulary. Returns the corrected query string (lowercased, space-joined),
67
- * or null when no term corrects to a different word or fuzzyCorrect is
68
- * unavailable. Only words of length >= 3 are considered (shorter tokens
69
- * can't be reliably corrected).
70
- */
71
- export async function correctQueryImpl(rlm, query) {
72
- if (typeof rlm.keywordSearch.fuzzyCorrect !== "function")
73
- return null;
74
- const terms = extractQueryTerms(query).filter((w) => w.length >= 3);
75
- // Vocabulary-nearest correction is reliable for identifier typo probes
76
- // ("useEffct") but unsafe for natural-language sentences: ordinary
77
- // Portuguese words were rewritten to unrelated English code tokens and
78
- // added as an entire extra RRF stream.
79
- if (terms.length !== 1)
80
- return null;
81
- const corrected = [];
82
- let changed = false;
83
- for (const term of terms) {
84
- const fix = await rlm.keywordSearch.fuzzyCorrect(term);
85
- if (fix && fix !== term) {
86
- corrected.push(fix);
87
- changed = true;
88
- }
89
- else {
90
- corrected.push(term);
91
- }
92
- }
93
- return changed ? corrected.join(" ") : null;
94
- }
95
16
  /**
96
17
  * Phase 7c: build the graph-neighbor RRF stream. BFS depth-2 over outgoing
97
18
  * memory-graph edges; resolved to SearchResults via the memory repository at
@@ -112,7 +33,7 @@ export async function correctQueryImpl(rlm, query) {
112
33
  * appends the stream when non-empty, so `resultSets.length` (and thus the
113
34
  * `search:reranked` streamCount) always reflects the real stream count.
114
35
  */
115
- export async function buildGraphStreamImpl(_rlm, resultSets, maxResults, projectId, reportDegradation) {
36
+ export async function buildGraphStream(resultSets, maxResults, projectId, reportDegradation) {
116
37
  try {
117
38
  // Seed candidates = top-N ids + derived filePath/symbol anchors from the
118
39
  // first (vector) stream's chunk metadata.
@@ -234,4 +155,4 @@ export async function buildGraphStreamImpl(_rlm, resultSets, maxResults, project
234
155
  return [];
235
156
  }
236
157
  }
237
- //# sourceMappingURL=rlm-synapse.js.map
158
+ //# sourceMappingURL=graph-stream.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"graph-stream.js","sourceRoot":"","sources":["../../../src/services/search/graph-stream.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,101 @@
1
+ /**
2
+ * hybrid-search — the hybrid retrieval capability (design.md §4.1).
3
+ *
4
+ * PR-B capability module, completed at T13. T9 created it with `correctQuery`
5
+ * alone; T13 moved `search`, `addContextToResults`, `extractPreview`,
6
+ * `calculateAvgScore` and `filterByPatterns` here, and `rlm-search.ts` dies whole
7
+ * in that commit — the fourth `rlm-*.ts` source to do so, and the last. This file
8
+ * has never heard of ContextualSearchRLM, which is what takes the root's foreign
9
+ * reach 14 → 1 and closes G-HUB (§3.4). `correctQuery` arrived from
10
+ * rlm-synapse.ts, not rlm-search.ts: it reads `keywordSearch`, the collaborator
11
+ * this module already owns, and its only caller is `search` (§4.2).
12
+ * `extractQueryTerms` / `applyProximityRerank` are *imported* from
13
+ * lexical-search.ts, never moved: that module carries a `data/` importer and is
14
+ * PR-C's to place (§5.4, PR-C-BOUNDARY). Behavior is byte-preserved from both
15
+ * sources — bodies verbatim, `rlm.<member>` rewritten per the disposition on
16
+ * `HybridSearchDeps` below and in full in tasks.md.
17
+ */
18
+ import { SearchResult } from "@massa-ai/shared";
19
+ import type { QueryUnderstandingService } from "./query-understanding.js";
20
+ import type { getKeywordSearch } from "../../data/keyword/keyword-search-factory.js";
21
+ import type { getVectorStore } from "../../data/vector/vector-store-factory.js";
22
+ import type { getSearchCache } from "./cache-factory.js";
23
+ import type { getSearchAnalytics } from "./analytics-factory.js";
24
+ import { type SearchDegradation, type SearchDegradationReporter } from "./search-diagnostics.js";
25
+ /**
26
+ * The narrow dependency record for this module (design.md §4.4) — exactly the
27
+ * collaborators §2.1 shows these surfaces read, and nothing else. §2.1 records
28
+ * `searchImpl` reading **13** facade members, the highest arity in the matrix;
29
+ * each one's disposition was decided by measuring the instance-stub sites that
30
+ * reach it, not by reading §4.1's "injected collaborators" column, which names
31
+ * five and is a store list rather than a member list. **The disposition table,
32
+ * the stub-site counts, the sweep method and the two-variant `queryUnderstanding`
33
+ * simulation are in tasks.md, "T13 — the disposition of §2.1's thirteen".**
34
+ *
35
+ * Four invariants this file must keep, each with a measurement behind it there:
36
+ *
37
+ * 1. `queryUnderstanding` stays `Pick<>`-narrowed — honest typing per §4.4, and
38
+ * **not** a fired sensor: bare nominal reaches 1, under the ceiling of 3.
39
+ * 2. The three callbacks stay **per-call arrow wrappers** — never `.bind(this)`,
40
+ * never bare method references, both of which resolve at *assembly* time.
41
+ * `buildGraphStream` and `addContextToResults` are each stubbed on the
42
+ * instance at 6 sites; a module-local call disables all twelve silently.
43
+ * 3. `ensureInitialized` is **not** a member of this record, and `search` must
44
+ * not call it. The root hoists it — carrying the `searchBackendUnavailable`
45
+ * wrap `searchImpl` used to apply — because the five stores below are
46
+ * snapshotted **by value**, so a record assembled before init holds five
47
+ * `undefined`s. Measured: rlm-search 31 → 15/16 the other way round.
48
+ * 4. The five stores stay required and keep the root's own field types — their
49
+ * originals were bare reads off definite-assigned fields with no fallback, so
50
+ * an absent store must keep throwing exactly where it did.
51
+ *
52
+ * `hybrid-search-late-bind.test.ts` test 4 is the compensating control for
53
+ * invariant 2, and what makes the coverage file's three `expect.any(Function)`
54
+ * keys acceptable rather than a relaxation. `correctQuery` takes this whole
55
+ * record while reading one field of it — the `getAnalytics`/`IndexAdminDeps`
56
+ * shape from T12; §4.4's narrowness is a property of the *module*'s record, not
57
+ * of each surface's parameter list.
58
+ */
59
+ export interface HybridSearchDeps {
60
+ keywordSearch: Awaited<ReturnType<typeof getKeywordSearch>>;
61
+ vectorStore: Awaited<ReturnType<typeof getVectorStore>>;
62
+ searchCache: Awaited<ReturnType<typeof getSearchCache>>;
63
+ analytics: Awaited<ReturnType<typeof getSearchAnalytics>>;
64
+ queryUnderstanding: Pick<QueryUnderstandingService, "understand">;
65
+ buildGraphStream: (resultSets: SearchResult[][], maxResults: number, projectId?: string, reportDegradation?: SearchDegradationReporter) => Promise<SearchResult[]>;
66
+ addContextToResults: (results: SearchResult[], projectId: string) => Promise<SearchResult[]>;
67
+ applySynapseState: (baseResults: SearchResult[], query: string, projectId: string, sessionId?: string, reportDegradation?: SearchDegradationReporter) => Promise<SearchResult[]>;
68
+ }
69
+ export type SearchOptions = {
70
+ maxResults?: number;
71
+ minScore?: number;
72
+ explainScores?: boolean;
73
+ includeFilters?: string[];
74
+ excludeFilters?: string[];
75
+ /** Phase 2: Synapse session id forwarded for future Synapse-biased fusion. */
76
+ sessionId?: string;
77
+ /** Receives bounded, sanitized evidence for optional search failures. */
78
+ onDegradations?: (degradations: readonly SearchDegradation[]) => void;
79
+ };
80
+ export declare function search(deps: HybridSearchDeps, query: string, projectId: string, options?: SearchOptions): Promise<SearchResult[]>;
81
+ /**
82
+ * Fuzzy-correct each non-stopword query term via the keyword store's
83
+ * vocabulary. Returns the corrected query string (lowercased, space-joined),
84
+ * or null when no term corrects to a different word or fuzzyCorrect is
85
+ * unavailable. Only words of length >= 3 are considered (shorter tokens
86
+ * can't be reliably corrected).
87
+ */
88
+ export declare function correctQuery(deps: HybridSearchDeps, query: string): Promise<string | null>;
89
+ /**
90
+ * Takes **no deps record** (§4.4): §2.1 shows its only facade read was
91
+ * `extractPreview`, which now lives beside it here, so the honest parameter list
92
+ * is the data alone — the shape `fuseResults` and `buildGraphStream` already
93
+ * have. GMS-03 AC-1 is satisfied by the absent facade argument, not by a record.
94
+ * `search` still reaches it through `deps.addContextToResults` rather than
95
+ * calling it module-locally — see the 6 stub sites noted above.
96
+ */
97
+ export declare function addContextToResults(results: SearchResult[], _projectId: string): Promise<SearchResult[]>;
98
+ export declare function extractPreview(content: string, maxLines?: number): string;
99
+ export declare function calculateAvgScore(results: SearchResult[]): number;
100
+ export declare function filterByPatterns(results: SearchResult[], include?: string[], exclude?: string[]): SearchResult[];
101
+ //# sourceMappingURL=hybrid-search.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hybrid-search.d.ts","sourceRoot":"","sources":["../../../src/services/search/hybrid-search.ts"],"names":[],"mappings":"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"}
@@ -1,25 +1,28 @@
1
1
  /**
2
- * rlm-search — search god-method + fusion + scoring + context delegates
3
- * for ContextualSearchRLM.
2
+ * hybrid-search — the hybrid retrieval capability (design.md §4.1).
4
3
  *
5
- * Extracted (M14 Phase 3, T3.3) from contextual-search-rlm.ts. Behavior is
6
- * byte-preserved: bodies moved verbatim with `this` → `rlm`.
4
+ * PR-B capability module, completed at T13. T9 created it with `correctQuery`
5
+ * alone; T13 moved `search`, `addContextToResults`, `extractPreview`,
6
+ * `calculateAvgScore` and `filterByPatterns` here, and `rlm-search.ts` dies whole
7
+ * in that commit — the fourth `rlm-*.ts` source to do so, and the last. This file
8
+ * has never heard of ContextualSearchRLM, which is what takes the root's foreign
9
+ * reach 14 → 1 and closes G-HUB (§3.4). `correctQuery` arrived from
10
+ * rlm-synapse.ts, not rlm-search.ts: it reads `keywordSearch`, the collaborator
11
+ * this module already owns, and its only caller is `search` (§4.2).
12
+ * `extractQueryTerms` / `applyProximityRerank` are *imported* from
13
+ * lexical-search.ts, never moved: that module carries a `data/` importer and is
14
+ * PR-C's to place (§5.4, PR-C-BOUNDARY). Behavior is byte-preserved from both
15
+ * sources — bodies verbatim, `rlm.<member>` rewritten per the disposition on
16
+ * `HybridSearchDeps` below and in full in tasks.md.
7
17
  */
8
18
  import { logger, config } from "@massa-ai/shared";
9
19
  import { minimatch } from "minimatch";
10
20
  import { buildRewrittenFTSQuery } from "./query-understanding.js";
11
- import { applyProximityRerank } from "./lexical-search.js";
21
+ import { applyProximityRerank, extractQueryTerms } from "./lexical-search.js";
12
22
  import { eventBus } from "../events/event-bus.js";
23
+ import { fuseResults } from "./result-fusion.js";
13
24
  import { recordSearchDegradation, recordSearchFailure, searchBackendUnavailable, SearchServiceError, storeCorruption, } from "./search-diagnostics.js";
14
- export async function searchImpl(rlm, query, projectId, options = {}) {
15
- try {
16
- await rlm.ensureInitialized();
17
- }
18
- catch (error) {
19
- const failure = searchBackendUnavailable("search_initialization", error);
20
- recordSearchFailure(failure, projectId);
21
- throw failure;
22
- }
25
+ export async function search(deps, query, projectId, options = {}) {
23
26
  const maxResults = options.maxResults ?? 10;
24
27
  const minScore = options.minScore ?? 0.3;
25
28
  const explainScores = options.explainScores || false;
@@ -82,7 +85,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
82
85
  };
83
86
  let cachedResults;
84
87
  try {
85
- cachedResults = await rlm.searchCache.get(query, projectId, cacheOptions);
88
+ cachedResults = await deps.searchCache.get(query, projectId, cacheOptions);
86
89
  }
87
90
  catch (error) {
88
91
  const failure = searchBackendUnavailable("search_cache_read", error);
@@ -102,14 +105,14 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
102
105
  });
103
106
  // Track cache hit
104
107
  try {
105
- rlm.analytics.trackSearch({
108
+ deps.analytics.trackSearch({
106
109
  timestamp: Date.now(),
107
110
  projectId,
108
111
  query,
109
112
  resultCount: cachedResults.length,
110
113
  duration,
111
114
  cacheHit: true,
112
- score: rlm.calculateAvgScore(cachedResults),
115
+ score: calculateAvgScore(cachedResults),
113
116
  });
114
117
  }
115
118
  catch {
@@ -123,7 +126,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
123
126
  preciseMs: `${(endTime - startTime).toFixed(3)}ms`,
124
127
  });
125
128
  try {
126
- return await rlm.applySynapseState(cachedResults, query, projectId, options.sessionId, degrade);
129
+ return await deps.applySynapseState(cachedResults, query, projectId, options.sessionId, degrade);
127
130
  }
128
131
  catch {
129
132
  degrade("SYNAPSE_UNAVAILABLE", "synapse");
@@ -139,7 +142,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
139
142
  try {
140
143
  const qu = config.get("search").queryUnderstanding;
141
144
  if (qu?.enabled && query.trim()) {
142
- understood = await rlm.queryUnderstanding.understand(query, projectId);
145
+ understood = await deps.queryUnderstanding.understand(query, projectId);
143
146
  if (!understood) {
144
147
  degrade("QUERY_UNDERSTANDING_UNAVAILABLE", "query_understanding");
145
148
  }
@@ -162,16 +165,16 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
162
165
  degrade("SEARCH_AUDIT_UNAVAILABLE", "search_query_rewritten_event");
163
166
  }
164
167
  const rewrittenFTS = buildRewrittenFTSQuery(query, understood.keywords);
165
- const vectorPromise = rlm.vectorStore
168
+ const vectorPromise = deps.vectorStore
166
169
  .search(query, retrievalLimit, projectId)
167
170
  .catch((error) => { throw searchBackendUnavailable("vector_search", error); });
168
171
  const keywordPromise = disableKeyword
169
172
  ? Promise.resolve([])
170
- : rlm.keywordSearch
173
+ : deps.keywordSearch
171
174
  .searchWithFilter(rewrittenFTS, { projectId }, retrievalLimit)
172
175
  .catch((error) => { throw searchBackendUnavailable("keyword_search", error); });
173
176
  const hydePromise = understood.hydeVector
174
- ? rlm.vectorStore
177
+ ? deps.vectorStore
175
178
  .searchByEmbedding(understood.hydeVector, retrievalLimit, projectId)
176
179
  .catch(() => {
177
180
  degrade("QUERY_UNDERSTANDING_UNAVAILABLE", "hyde_search");
@@ -195,18 +198,18 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
195
198
  // streams fuse via RRF; empty streams contribute nothing.
196
199
  const fetchN = retrievalLimit;
197
200
  const [vectorResults, keywordResults, trigramResults] = await Promise.all([
198
- rlm.vectorStore
201
+ deps.vectorStore
199
202
  .search(query, fetchN, projectId)
200
203
  .catch((error) => { throw searchBackendUnavailable("vector_search", error); }),
201
204
  disableKeyword
202
205
  ? Promise.resolve([])
203
- : rlm.keywordSearch
206
+ : deps.keywordSearch
204
207
  .searchWithFilter(query, { projectId }, fetchN)
205
208
  .catch((error) => { throw searchBackendUnavailable("keyword_search", error); }),
206
209
  // Trigram stream (best-effort; [] when tokenizer unavailable).
207
- disableKeyword || !rlm.keywordSearch.searchTrigram
210
+ disableKeyword || !deps.keywordSearch.searchTrigram
208
211
  ? Promise.resolve([])
209
- : rlm.keywordSearch
212
+ : deps.keywordSearch
210
213
  .searchTrigram(query, { projectId }, fetchN)
211
214
  .catch(() => {
212
215
  degrade("TRIGRAM_UNAVAILABLE", "trigram_search");
@@ -224,10 +227,10 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
224
227
  // add both as RRF streams. This recovers typos like "useEffct" →
225
228
  // "useEffect" that porter/trigram miss. Best-effort; skipped when no
226
229
  // correction applies or fuzzyCorrect is unavailable.
227
- if (!disableKeyword && typeof rlm.keywordSearch.fuzzyCorrect === "function") {
230
+ if (!disableKeyword && typeof deps.keywordSearch.fuzzyCorrect === "function") {
228
231
  let corrected = null;
229
232
  try {
230
- corrected = await rlm.correctQuery(query);
233
+ corrected = await correctQuery(deps, query);
231
234
  }
232
235
  catch {
233
236
  degrade("FUZZY_SEARCH_UNAVAILABLE", "fuzzy_correction");
@@ -235,14 +238,14 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
235
238
  if (corrected && corrected !== query.toLowerCase().trim()) {
236
239
  try {
237
240
  const [fuzzyKeyword, fuzzyTrigram] = await Promise.all([
238
- rlm.keywordSearch
241
+ deps.keywordSearch
239
242
  .searchWithFilter(corrected, { projectId }, fetchN)
240
243
  .catch(() => {
241
244
  degrade("FUZZY_SEARCH_UNAVAILABLE", "fuzzy_keyword_search");
242
245
  return [];
243
246
  }),
244
- rlm.keywordSearch.searchTrigram
245
- ? rlm.keywordSearch
247
+ deps.keywordSearch.searchTrigram
248
+ ? deps.keywordSearch
246
249
  .searchTrigram(corrected, { projectId }, fetchN)
247
250
  .catch(() => {
248
251
  degrade("FUZZY_SEARCH_UNAVAILABLE", "fuzzy_trigram_search");
@@ -274,7 +277,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
274
277
  // the actual stream count). No graph-stream throw escapes this optional path.
275
278
  let graphStream = [];
276
279
  try {
277
- graphStream = await rlm.buildGraphStream(resultSets, maxResults, projectId, degrade);
280
+ graphStream = await deps.buildGraphStream(resultSets, maxResults, projectId, degrade);
278
281
  }
279
282
  catch {
280
283
  degrade("GRAPH_AUGMENTATION_UNAVAILABLE", "graph_augmentation");
@@ -283,7 +286,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
283
286
  resultSets = [...resultSets, graphStream];
284
287
  }
285
288
  // Combine results using RRF (with score explanation if requested)
286
- const fusedResults = rlm.fuseResults(resultSets, query, explainScores);
289
+ const fusedResults = fuseResults(resultSets, query, explainScores);
287
290
  // A2: proximity + title re-ranking pass (post-RRF, pre-filter). Stable
288
291
  // re-rank on top of RRF: boosts results whose title contains query terms
289
292
  // and whose body positions the terms close together; code chunks get a
@@ -321,7 +324,7 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
321
324
  let filteredByPattern = fusedReranked;
322
325
  if (includeFilters || excludeFilters) {
323
326
  const filterStartTime = performance.now();
324
- filteredByPattern = rlm.filterByPatterns(fusedReranked, includeFilters, excludeFilters);
327
+ filteredByPattern = filterByPatterns(fusedReranked, includeFilters, excludeFilters);
325
328
  const filterDuration = performance.now() - filterStartTime;
326
329
  logger.debug("Applied file pattern filters", {
327
330
  beforeFilter: fusedReranked.length,
@@ -367,14 +370,14 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
367
370
  // Add context to results
368
371
  let withContext;
369
372
  try {
370
- withContext = await rlm.addContextToResults(filtered, projectId);
373
+ withContext = await deps.addContextToResults(filtered, projectId);
371
374
  }
372
375
  catch (error) {
373
376
  throw storeCorruption("search_result_hydration", error);
374
377
  }
375
378
  // Cache the results
376
379
  try {
377
- await rlm.searchCache.set(query, projectId, withContext, cacheOptions);
380
+ await deps.searchCache.set(query, projectId, withContext, cacheOptions);
378
381
  }
379
382
  catch (error) {
380
383
  throw searchBackendUnavailable("search_cache_write", error);
@@ -382,14 +385,14 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
382
385
  const duration = Math.round(performance.now() - startTime); // Use performance.now() for consistency
383
386
  // Track cache miss
384
387
  try {
385
- rlm.analytics.trackSearch({
388
+ deps.analytics.trackSearch({
386
389
  timestamp: Date.now(),
387
390
  projectId,
388
391
  query,
389
392
  resultCount: withContext.length,
390
393
  duration,
391
394
  cacheHit: false,
392
- score: rlm.calculateAvgScore(withContext),
395
+ score: calculateAvgScore(withContext),
393
396
  });
394
397
  }
395
398
  catch {
@@ -398,11 +401,11 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
398
401
  logger.info("Contextual search completed", {
399
402
  projectId,
400
403
  totalResults: withContext.length,
401
- avgScore: rlm.calculateAvgScore(withContext),
404
+ avgScore: calculateAvgScore(withContext),
402
405
  duration,
403
406
  });
404
407
  try {
405
- return await rlm.applySynapseState(withContext, query, projectId, options.sessionId, degrade);
408
+ return await deps.applySynapseState(withContext, query, projectId, options.sessionId, degrade);
406
409
  }
407
410
  catch {
408
411
  degrade("SYNAPSE_UNAVAILABLE", "synapse");
@@ -420,8 +423,48 @@ export async function searchImpl(rlm, query, projectId, options = {}) {
420
423
  throw error;
421
424
  }
422
425
  }
426
+ // ── correctQuery ─────────────────────────────────────────────────────────────
427
+ /**
428
+ * Fuzzy-correct each non-stopword query term via the keyword store's
429
+ * vocabulary. Returns the corrected query string (lowercased, space-joined),
430
+ * or null when no term corrects to a different word or fuzzyCorrect is
431
+ * unavailable. Only words of length >= 3 are considered (shorter tokens
432
+ * can't be reliably corrected).
433
+ */
434
+ export async function correctQuery(deps, query) {
435
+ if (typeof deps.keywordSearch.fuzzyCorrect !== "function")
436
+ return null;
437
+ const terms = extractQueryTerms(query).filter((w) => w.length >= 3);
438
+ // Vocabulary-nearest correction is reliable for identifier typo probes
439
+ // ("useEffct") but unsafe for natural-language sentences: ordinary
440
+ // Portuguese words were rewritten to unrelated English code tokens and
441
+ // added as an entire extra RRF stream.
442
+ if (terms.length !== 1)
443
+ return null;
444
+ const corrected = [];
445
+ let changed = false;
446
+ for (const term of terms) {
447
+ const fix = await deps.keywordSearch.fuzzyCorrect(term);
448
+ if (fix && fix !== term) {
449
+ corrected.push(fix);
450
+ changed = true;
451
+ }
452
+ else {
453
+ corrected.push(term);
454
+ }
455
+ }
456
+ return changed ? corrected.join(" ") : null;
457
+ }
423
458
  // ── addContextToResults ──────────────────────────────────────────────────────
424
- export async function addContextToResultsImpl(rlm, results, _projectId) {
459
+ /**
460
+ * Takes **no deps record** (§4.4): §2.1 shows its only facade read was
461
+ * `extractPreview`, which now lives beside it here, so the honest parameter list
462
+ * is the data alone — the shape `fuseResults` and `buildGraphStream` already
463
+ * have. GMS-03 AC-1 is satisfied by the absent facade argument, not by a record.
464
+ * `search` still reaches it through `deps.addContextToResults` rather than
465
+ * calling it module-locally — see the 6 stub sites noted above.
466
+ */
467
+ export async function addContextToResults(results, _projectId) {
425
468
  return results.map((result) => {
426
469
  const metadata = result.metadata;
427
470
  const filePath = metadata?.filePath;
@@ -437,7 +480,7 @@ export async function addContextToResultsImpl(rlm, results, _projectId) {
437
480
  filePath,
438
481
  lineStart,
439
482
  lineEnd,
440
- preview: rlm.extractPreview(result.content),
483
+ preview: extractPreview(result.content),
441
484
  },
442
485
  },
443
486
  };
@@ -446,20 +489,20 @@ export async function addContextToResultsImpl(rlm, results, _projectId) {
446
489
  });
447
490
  }
448
491
  // ── extractPreview ───────────────────────────────────────────────────────────
449
- export function extractPreviewImpl(content, maxLines = 5) {
492
+ export function extractPreview(content, maxLines = 5) {
450
493
  const lines = content.split("\n");
451
494
  const preview = lines.slice(0, maxLines).join("\n");
452
495
  return lines.length > maxLines ? preview + "\n..." : preview;
453
496
  }
454
497
  // ── calculateAvgScore ────────────────────────────────────────────────────────
455
- export function calculateAvgScoreImpl(results) {
498
+ export function calculateAvgScore(results) {
456
499
  if (results.length === 0)
457
500
  return 0;
458
501
  const sum = results.reduce((acc, r) => acc + r.score, 0);
459
502
  return sum / results.length;
460
503
  }
461
504
  // ── filterByPatterns ─────────────────────────────────────────────────────────
462
- export function filterByPatternsImpl(results, include, exclude) {
505
+ export function filterByPatterns(results, include, exclude) {
463
506
  if (!include && !exclude) {
464
507
  return results;
465
508
  }
@@ -482,4 +525,4 @@ export function filterByPatternsImpl(results, include, exclude) {
482
525
  return true;
483
526
  });
484
527
  }
485
- //# sourceMappingURL=rlm-search.js.map
528
+ //# sourceMappingURL=hybrid-search.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hybrid-search.js","sourceRoot":"","sources":["../../../src/services/search/hybrid-search.ts"],"names":[],"mappings":"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"}