@mhalder/qdrant-mcp-server 3.3.3 → 3.3.4

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 (168) hide show
  1. package/.github/workflows/ci.yml +0 -2
  2. package/.github/workflows/claude-code-review.yml +1 -1
  3. package/CHANGELOG.md +6 -0
  4. package/README.md +1 -1
  5. package/biome.json +3 -2
  6. package/build/code/chunker/tree-sitter-chunker.d.ts.map +1 -1
  7. package/build/code/chunker/tree-sitter-chunker.js +2 -12
  8. package/build/code/chunker/tree-sitter-chunker.js.map +1 -1
  9. package/build/code/indexer.d.ts.map +1 -1
  10. package/build/code/indexer.js +12 -18
  11. package/build/code/indexer.js.map +1 -1
  12. package/build/code/scanner.js +1 -1
  13. package/build/code/scanner.js.map +1 -1
  14. package/build/embeddings/cohere.d.ts +1 -1
  15. package/build/embeddings/cohere.d.ts.map +1 -1
  16. package/build/embeddings/cohere.js +2 -2
  17. package/build/embeddings/cohere.js.map +1 -1
  18. package/build/embeddings/cohere.test.js +1 -5
  19. package/build/embeddings/cohere.test.js.map +1 -1
  20. package/build/embeddings/factory.d.ts +1 -1
  21. package/build/embeddings/factory.d.ts.map +1 -1
  22. package/build/embeddings/factory.js +7 -9
  23. package/build/embeddings/factory.js.map +1 -1
  24. package/build/embeddings/factory.test.js +3 -3
  25. package/build/embeddings/factory.test.js.map +1 -1
  26. package/build/embeddings/ollama.d.ts +1 -1
  27. package/build/embeddings/ollama.d.ts.map +1 -1
  28. package/build/embeddings/ollama.js +6 -8
  29. package/build/embeddings/ollama.js.map +1 -1
  30. package/build/embeddings/ollama.test.js +2 -6
  31. package/build/embeddings/ollama.test.js.map +1 -1
  32. package/build/embeddings/openai.d.ts +1 -1
  33. package/build/embeddings/openai.d.ts.map +1 -1
  34. package/build/embeddings/openai.js +4 -7
  35. package/build/embeddings/openai.js.map +1 -1
  36. package/build/embeddings/openai.test.js +3 -12
  37. package/build/embeddings/openai.test.js.map +1 -1
  38. package/build/embeddings/sparse.test.js +12 -2
  39. package/build/embeddings/sparse.test.js.map +1 -1
  40. package/build/embeddings/voyage.d.ts +1 -1
  41. package/build/embeddings/voyage.d.ts.map +1 -1
  42. package/build/embeddings/voyage.js +2 -3
  43. package/build/embeddings/voyage.js.map +1 -1
  44. package/build/embeddings/voyage.test.js +2 -6
  45. package/build/embeddings/voyage.test.js.map +1 -1
  46. package/build/git/chunker.d.ts.map +1 -1
  47. package/build/git/chunker.js +2 -2
  48. package/build/git/chunker.js.map +1 -1
  49. package/build/git/chunker.test.js +1 -1
  50. package/build/git/chunker.test.js.map +1 -1
  51. package/build/git/extractor.d.ts.map +1 -1
  52. package/build/git/extractor.integration.test.js +9 -5
  53. package/build/git/extractor.integration.test.js.map +1 -1
  54. package/build/git/extractor.js +1 -1
  55. package/build/git/extractor.js.map +1 -1
  56. package/build/git/extractor.test.js +2 -2
  57. package/build/git/extractor.test.js.map +1 -1
  58. package/build/git/index.d.ts +4 -4
  59. package/build/git/index.d.ts.map +1 -1
  60. package/build/git/index.js +3 -3
  61. package/build/git/index.js.map +1 -1
  62. package/build/git/indexer.d.ts.map +1 -1
  63. package/build/git/indexer.js +9 -21
  64. package/build/git/indexer.js.map +1 -1
  65. package/build/git/indexer.test.js +4 -8
  66. package/build/git/indexer.test.js.map +1 -1
  67. package/build/git/sync/synchronizer.d.ts.map +1 -1
  68. package/build/git/sync/synchronizer.js.map +1 -1
  69. package/build/git/sync/synchronizer.test.js +4 -2
  70. package/build/git/sync/synchronizer.test.js.map +1 -1
  71. package/build/index.js +5 -9
  72. package/build/index.js.map +1 -1
  73. package/build/index.test.js +3 -3
  74. package/build/index.test.js.map +1 -1
  75. package/build/logger.d.ts.map +1 -1
  76. package/build/logger.js +1 -9
  77. package/build/logger.js.map +1 -1
  78. package/build/prompts/register.d.ts.map +1 -1
  79. package/build/prompts/register.js.map +1 -1
  80. package/build/qdrant/client.d.ts.map +1 -1
  81. package/build/qdrant/client.js.map +1 -1
  82. package/build/qdrant/client.test.js +10 -34
  83. package/build/qdrant/client.test.js.map +1 -1
  84. package/build/resources/index.d.ts +1 -1
  85. package/build/resources/index.d.ts.map +1 -1
  86. package/build/resources/index.js +1 -1
  87. package/build/resources/index.js.map +1 -1
  88. package/build/tools/code.d.ts.map +1 -1
  89. package/build/tools/code.js +3 -9
  90. package/build/tools/code.js.map +1 -1
  91. package/build/tools/collection.d.ts.map +1 -1
  92. package/build/tools/collection.js +1 -3
  93. package/build/tools/collection.js.map +1 -1
  94. package/build/tools/document.d.ts.map +1 -1
  95. package/build/tools/document.js +1 -1
  96. package/build/tools/document.js.map +1 -1
  97. package/build/tools/federated.d.ts.map +1 -1
  98. package/build/tools/federated.js +15 -6
  99. package/build/tools/federated.js.map +1 -1
  100. package/build/tools/federated.test.js +18 -22
  101. package/build/tools/federated.test.js.map +1 -1
  102. package/build/tools/git-history.d.ts.map +1 -1
  103. package/build/tools/git-history.js +3 -7
  104. package/build/tools/git-history.js.map +1 -1
  105. package/build/tools/index.d.ts.map +1 -1
  106. package/build/tools/index.js.map +1 -1
  107. package/build/tools/logging.d.ts.map +1 -1
  108. package/build/tools/logging.js +1 -3
  109. package/build/tools/logging.js.map +1 -1
  110. package/build/tools/logging.test.js +1 -1
  111. package/build/tools/logging.test.js.map +1 -1
  112. package/build/tools/schemas.d.ts.map +1 -1
  113. package/build/tools/schemas.js +17 -64
  114. package/build/tools/schemas.js.map +1 -1
  115. package/build/tools/search.d.ts.map +1 -1
  116. package/build/tools/search.js +1 -1
  117. package/build/tools/search.js.map +1 -1
  118. package/commitlint.config.js +12 -23
  119. package/package.json +1 -1
  120. package/scripts/verify-providers.js +12 -32
  121. package/src/code/chunker/tree-sitter-chunker.ts +9 -35
  122. package/src/code/indexer.ts +45 -107
  123. package/src/code/scanner.ts +1 -1
  124. package/src/embeddings/cohere.test.ts +17 -45
  125. package/src/embeddings/cohere.ts +10 -17
  126. package/src/embeddings/factory.test.ts +18 -18
  127. package/src/embeddings/factory.ts +18 -25
  128. package/src/embeddings/ollama.test.ts +38 -67
  129. package/src/embeddings/ollama.ts +15 -27
  130. package/src/embeddings/openai.test.ts +17 -53
  131. package/src/embeddings/openai.ts +11 -22
  132. package/src/embeddings/sparse.test.ts +12 -2
  133. package/src/embeddings/voyage.test.ts +39 -80
  134. package/src/embeddings/voyage.ts +9 -13
  135. package/src/git/chunker.test.ts +1 -1
  136. package/src/git/chunker.ts +6 -22
  137. package/src/git/extractor.integration.test.ts +12 -16
  138. package/src/git/extractor.test.ts +21 -35
  139. package/src/git/extractor.ts +14 -36
  140. package/src/git/index.ts +9 -10
  141. package/src/git/indexer.test.ts +29 -57
  142. package/src/git/indexer.ts +38 -86
  143. package/src/git/sync/synchronizer.test.ts +6 -9
  144. package/src/git/sync/synchronizer.ts +2 -5
  145. package/src/index.test.ts +7 -9
  146. package/src/index.ts +34 -80
  147. package/src/logger.ts +3 -14
  148. package/src/prompts/register.ts +3 -10
  149. package/src/qdrant/client.test.ts +63 -169
  150. package/src/qdrant/client.ts +19 -45
  151. package/src/resources/index.ts +4 -10
  152. package/src/tools/code.ts +43 -66
  153. package/src/tools/collection.ts +19 -38
  154. package/src/tools/document.ts +10 -19
  155. package/src/tools/federated.test.ts +34 -57
  156. package/src/tools/federated.ts +88 -108
  157. package/src/tools/git-history.ts +32 -60
  158. package/src/tools/index.ts +1 -4
  159. package/src/tools/logging.test.ts +10 -10
  160. package/src/tools/logging.ts +8 -18
  161. package/src/tools/schemas.ts +23 -78
  162. package/src/tools/search.ts +77 -94
  163. package/tests/code/chunker/tree-sitter-chunker.test.ts +6 -19
  164. package/tests/code/indexer.test.ts +100 -192
  165. package/tests/code/integration.test.ts +61 -117
  166. package/tests/code/scanner.test.ts +12 -39
  167. package/tests/code/sync/snapshot.test.ts +4 -14
  168. package/tests/code/sync/synchronizer.test.ts +10 -40
@@ -33,7 +33,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
33
33
  name: string,
34
34
  vectorSize: number,
35
35
  distance: "Cosine" | "Euclid" | "Dot" = "Cosine",
36
- enableHybrid?: boolean,
36
+ enableHybrid?: boolean
37
37
  ): Promise<void> {
38
38
  this.collections.set(name, {
39
39
  vectorSize,
@@ -56,10 +56,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
56
56
  this.points.set(collectionName, [...filtered, ...points]);
57
57
  }
58
58
 
59
- async addPointsWithSparse(
60
- collectionName: string,
61
- points: any[],
62
- ): Promise<void> {
59
+ async addPointsWithSparse(collectionName: string, points: any[]): Promise<void> {
63
60
  await this.addPoints(collectionName, points);
64
61
  }
65
62
 
@@ -67,7 +64,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
67
64
  collectionName: string,
68
65
  _vector: number[],
69
66
  limit: number,
70
- filter?: any,
67
+ filter?: any
71
68
  ): Promise<any[]> {
72
69
  const points = this.points.get(collectionName) || [];
73
70
  let filtered = points;
@@ -76,9 +73,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
76
73
  if (filter?.must) {
77
74
  for (const condition of filter.must) {
78
75
  if (condition.key === "fileExtension") {
79
- filtered = filtered.filter((p) =>
80
- condition.match.any.includes(p.payload.fileExtension),
81
- );
76
+ filtered = filtered.filter((p) => condition.match.any.includes(p.payload.fileExtension));
82
77
  }
83
78
  }
84
79
  }
@@ -95,7 +90,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
95
90
  vector: number[],
96
91
  _sparseVector: any,
97
92
  limit: number,
98
- filter?: any,
93
+ filter?: any
99
94
  ): Promise<any[]> {
100
95
  // Hybrid search returns similar results with slight boost
101
96
  const results = await this.search(collectionName, vector, limit, filter);
@@ -114,7 +109,7 @@ class MockQdrantManager implements Partial<QdrantManager> {
114
109
 
115
110
  async getPoint(
116
111
  collectionName: string,
117
- id: string | number,
112
+ id: string | number
118
113
  ): Promise<{ id: string | number; payload?: Record<string, any> } | null> {
119
114
  const points = this.points.get(collectionName) || [];
120
115
  const point = points.find((p) => p.id === id);
@@ -127,16 +122,11 @@ class MockQdrantManager implements Partial<QdrantManager> {
127
122
  };
128
123
  }
129
124
 
130
- async deletePointsByFilter(
131
- collectionName: string,
132
- filter: Record<string, any>,
133
- ): Promise<void> {
125
+ async deletePointsByFilter(collectionName: string, filter: Record<string, any>): Promise<void> {
134
126
  const points = this.points.get(collectionName) || [];
135
127
  const pathToDelete = filter?.must?.[0]?.match?.value;
136
128
  if (pathToDelete) {
137
- const filtered = points.filter(
138
- (p) => p.payload?.relativePath !== pathToDelete,
139
- );
129
+ const filtered = points.filter((p) => p.payload?.relativePath !== pathToDelete);
140
130
  this.points.set(collectionName, filtered);
141
131
  }
142
132
  }
@@ -151,20 +141,14 @@ class MockEmbeddingProvider implements EmbeddingProvider {
151
141
  return "mock-model";
152
142
  }
153
143
 
154
- async embed(
155
- text: string,
156
- ): Promise<{ embedding: number[]; dimensions: number }> {
144
+ async embed(text: string): Promise<{ embedding: number[]; dimensions: number }> {
157
145
  // Simple hash-based mock embedding
158
- const hash = text
159
- .split("")
160
- .reduce((acc, char) => acc + char.charCodeAt(0), 0);
146
+ const hash = text.split("").reduce((acc, char) => acc + char.charCodeAt(0), 0);
161
147
  const base = (hash % 100) / 100;
162
148
  return { embedding: new Array(384).fill(base), dimensions: 384 };
163
149
  }
164
150
 
165
- async embedBatch(
166
- texts: string[],
167
- ): Promise<Array<{ embedding: number[]; dimensions: number }>> {
151
+ async embedBatch(texts: string[]): Promise<Array<{ embedding: number[]; dimensions: number }>> {
168
152
  return Promise.all(texts.map((text) => this.embed(text)));
169
153
  }
170
154
  }
@@ -180,7 +164,7 @@ describe("CodeIndexer Integration Tests", () => {
180
164
  beforeEach(async () => {
181
165
  tempDir = join(
182
166
  tmpdir(),
183
- `qdrant-mcp-test-${Date.now()}-${Math.random().toString(36).substring(7)}`,
167
+ `qdrant-mcp-test-${Date.now()}-${Math.random().toString(36).substring(7)}`
184
168
  );
185
169
  codebaseDir = join(tempDir, "codebase");
186
170
  await fs.mkdir(codebaseDir, { recursive: true });
@@ -221,7 +205,7 @@ export class AuthService {
221
205
  return { token: 'jwt-token' };
222
206
  }
223
207
  }
224
- `,
208
+ `
225
209
  );
226
210
 
227
211
  await createTestFile(
@@ -233,7 +217,7 @@ export class RegistrationService {
233
217
  return { id: '123', email: user.email };
234
218
  }
235
219
  }
236
- `,
220
+ `
237
221
  );
238
222
 
239
223
  await createTestFile(
@@ -243,7 +227,7 @@ export class RegistrationService {
243
227
  export function validateEmail(email: string): boolean {
244
228
  return /^[^@]+@[^@]+\\.[^@]+$/.test(email);
245
229
  }
246
- `,
230
+ `
247
231
  );
248
232
 
249
233
  // Index the codebase
@@ -255,10 +239,7 @@ export function validateEmail(email: string): boolean {
255
239
  expect(indexStats.status).toBe("completed");
256
240
 
257
241
  // Search for authentication-related code
258
- const authResults = await indexer.searchCode(
259
- codebaseDir,
260
- "authentication login",
261
- );
242
+ const authResults = await indexer.searchCode(codebaseDir, "authentication login");
262
243
 
263
244
  expect(authResults.length).toBeGreaterThan(0);
264
245
  expect(authResults[0].language).toBe("typescript");
@@ -278,7 +259,7 @@ export function validateEmail(email: string): boolean {
278
259
  import express from 'express';
279
260
  const app = express();
280
261
  app.listen(3000);
281
- `,
262
+ `
282
263
  );
283
264
 
284
265
  await createTestFile(
@@ -287,7 +268,7 @@ app.listen(3000);
287
268
  `
288
269
  const API_URL = 'http://localhost:3000';
289
270
  fetch(API_URL).then(res => res.json());
290
- `,
271
+ `
291
272
  );
292
273
 
293
274
  await createTestFile(
@@ -296,7 +277,7 @@ fetch(API_URL).then(res => res.json());
296
277
  `
297
278
  def process_data(data):
298
279
  return [x * 2 for x in data]
299
- `,
280
+ `
300
281
  );
301
282
 
302
283
  const stats = await indexer.indexCodebase(codebaseDir);
@@ -322,7 +303,7 @@ console.log('First file loaded successfully');
322
303
  function init(): string {
323
304
  console.log('Initializing system');
324
305
  return 'ready';
325
- }`,
306
+ }`
326
307
  );
327
308
  await createTestFile(
328
309
  codebaseDir,
@@ -332,7 +313,7 @@ console.log('Second file loaded successfully');
332
313
  function start(): string {
333
314
  console.log('Starting application');
334
315
  return 'started';
335
- }`,
316
+ }`
336
317
  );
337
318
 
338
319
  const initialStats = await indexer.indexCodebase(codebaseDir);
@@ -354,7 +335,7 @@ export function process(): string {
354
335
  return status;
355
336
  }
356
337
 
357
- export const thirdValue = 3;`,
338
+ export const thirdValue = 3;`
358
339
  );
359
340
 
360
341
  // Incremental update
@@ -373,7 +354,7 @@ export const thirdValue = 3;`,
373
354
  await createTestFile(
374
355
  codebaseDir,
375
356
  "config.ts",
376
- "export const DEBUG_MODE = false;\nconsole.log('Debug mode off');",
357
+ "export const DEBUG_MODE = false;\nconsole.log('Debug mode off');"
377
358
  );
378
359
 
379
360
  await indexer.indexCodebase(codebaseDir);
@@ -382,7 +363,7 @@ export const thirdValue = 3;`,
382
363
  await createTestFile(
383
364
  codebaseDir,
384
365
  "config.ts",
385
- "export const DEBUG_MODE = true;\nconsole.log('Debug mode on');",
366
+ "export const DEBUG_MODE = true;\nconsole.log('Debug mode on');"
386
367
  );
387
368
 
388
369
  const updateStats = await indexer.reindexChanges(codebaseDir);
@@ -395,12 +376,12 @@ export const thirdValue = 3;`,
395
376
  await createTestFile(
396
377
  codebaseDir,
397
378
  "temp.ts",
398
- "export const tempValue = true;\nconsole.log('Temporary file created');\nfunction cleanup() { return null; }",
379
+ "export const tempValue = true;\nconsole.log('Temporary file created');\nfunction cleanup() { return null; }"
399
380
  );
400
381
  await createTestFile(
401
382
  codebaseDir,
402
383
  "keep.ts",
403
- "export const keepValue = true;\nconsole.log('Permanent file stays');\nfunction maintain() { return true; }",
384
+ "export const keepValue = true;\nconsole.log('Permanent file stays');\nfunction maintain() { return true; }"
404
385
  );
405
386
 
406
387
  await indexer.indexCodebase(codebaseDir);
@@ -419,17 +400,17 @@ export const thirdValue = 3;`,
419
400
  await createTestFile(
420
401
  codebaseDir,
421
402
  "file1.ts",
422
- "export const alpha = 1;\nconsole.log('Alpha file');",
403
+ "export const alpha = 1;\nconsole.log('Alpha file');"
423
404
  );
424
405
  await createTestFile(
425
406
  codebaseDir,
426
407
  "file2.ts",
427
- "export const beta = 2;\nconsole.log('Beta file');",
408
+ "export const beta = 2;\nconsole.log('Beta file');"
428
409
  );
429
410
  await createTestFile(
430
411
  codebaseDir,
431
412
  "file3.ts",
432
- "export const gamma = 3;\nconsole.log('Gamma file');",
413
+ "export const gamma = 3;\nconsole.log('Gamma file');"
433
414
  );
434
415
 
435
416
  await indexer.indexCodebase(codebaseDir);
@@ -438,12 +419,12 @@ export const thirdValue = 3;`,
438
419
  await createTestFile(
439
420
  codebaseDir,
440
421
  "file1.ts",
441
- "export const alpha = 100;\nconsole.log('Alpha modified');",
422
+ "export const alpha = 100;\nconsole.log('Alpha modified');"
442
423
  ); // Modified
443
424
  await createTestFile(
444
425
  codebaseDir,
445
426
  "file4.ts",
446
- "export const delta = 4;\nconsole.log('Delta file added');",
427
+ "export const delta = 4;\nconsole.log('Delta file added');"
447
428
  ); // Added
448
429
  await fs.unlink(join(codebaseDir, "file3.ts")); // Deleted
449
430
 
@@ -457,21 +438,9 @@ export const thirdValue = 3;`,
457
438
 
458
439
  describe("Search filtering and options", () => {
459
440
  beforeEach(async () => {
460
- await createTestFile(
461
- codebaseDir,
462
- "users.ts",
463
- "export class UserService {}",
464
- );
465
- await createTestFile(
466
- codebaseDir,
467
- "auth.ts",
468
- "export class AuthService {}",
469
- );
470
- await createTestFile(
471
- codebaseDir,
472
- "utils.js",
473
- "export function helper() {}",
474
- );
441
+ await createTestFile(codebaseDir, "users.ts", "export class UserService {}");
442
+ await createTestFile(codebaseDir, "auth.ts", "export class AuthService {}");
443
+ await createTestFile(codebaseDir, "utils.js", "export function helper() {}");
475
444
  await createTestFile(codebaseDir, "data.py", "class DataProcessor: pass");
476
445
 
477
446
  await indexer.indexCodebase(codebaseDir);
@@ -506,11 +475,7 @@ export const thirdValue = 3;`,
506
475
  });
507
476
 
508
477
  it("should support path pattern filtering", async () => {
509
- await createTestFile(
510
- codebaseDir,
511
- "src/api/endpoints.ts",
512
- "export const API = {}",
513
- );
478
+ await createTestFile(codebaseDir, "src/api/endpoints.ts", "export const API = {}");
514
479
  await indexer.indexCodebase(codebaseDir, { forceReindex: true });
515
480
 
516
481
  const results = await indexer.searchCode(codebaseDir, "export", {
@@ -524,35 +489,24 @@ export const thirdValue = 3;`,
524
489
  describe("Hybrid search workflow", () => {
525
490
  it("should enable and use hybrid search", async () => {
526
491
  const hybridConfig = { ...config, enableHybridSearch: true };
527
- const hybridIndexer = new CodeIndexer(
528
- qdrant as any,
529
- embeddings,
530
- hybridConfig,
531
- );
492
+ const hybridIndexer = new CodeIndexer(qdrant as any, embeddings, hybridConfig);
532
493
 
533
494
  await createTestFile(
534
495
  codebaseDir,
535
496
  "search.ts",
536
- "function performSearch(query: string) { return results; }",
497
+ "function performSearch(query: string) { return results; }"
537
498
  );
538
499
 
539
500
  await hybridIndexer.indexCodebase(codebaseDir);
540
501
 
541
- const results = await hybridIndexer.searchCode(
542
- codebaseDir,
543
- "search query",
544
- );
502
+ const results = await hybridIndexer.searchCode(codebaseDir, "search query");
545
503
 
546
504
  expect(results.length).toBeGreaterThan(0);
547
505
  });
548
506
 
549
507
  it("should fallback to standard search if hybrid not available", async () => {
550
508
  const hybridConfig = { ...config, enableHybridSearch: true };
551
- const hybridIndexer = new CodeIndexer(
552
- qdrant as any,
553
- embeddings,
554
- hybridConfig,
555
- );
509
+ const hybridIndexer = new CodeIndexer(qdrant as any, embeddings, hybridConfig);
556
510
 
557
511
  // Index without hybrid
558
512
  await createTestFile(
@@ -563,7 +517,7 @@ console.log('Test value configured successfully');
563
517
  function validate(): boolean {
564
518
  console.log('Validating test value');
565
519
  return testValue === true;
566
- }`,
520
+ }`
567
521
  );
568
522
  await indexer.indexCodebase(codebaseDir);
569
523
 
@@ -581,7 +535,7 @@ function validate(): boolean {
581
535
  await createTestFile(
582
536
  codebaseDir,
583
537
  `module${i}.ts`,
584
- `export function func${i}() { return ${i}; }`,
538
+ `export function func${i}() { return ${i}; }`
585
539
  );
586
540
  }
587
541
 
@@ -611,12 +565,12 @@ function validate(): boolean {
611
565
  await createTestFile(
612
566
  codebaseDir,
613
567
  "valid.ts",
614
- "export const validValue = true;\nconsole.log('Valid file');",
568
+ "export const validValue = true;\nconsole.log('Valid file');"
615
569
  );
616
570
  await createTestFile(
617
571
  codebaseDir,
618
572
  "secrets.ts",
619
- 'export const apiKey = "sk_test_FAKE_KEY_FOR_TESTING_NOT_REAL_KEY";\nconsole.log("Secrets file");',
573
+ 'export const apiKey = "sk_test_FAKE_KEY_FOR_TESTING_NOT_REAL_KEY";\nconsole.log("Secrets file");'
620
574
  );
621
575
 
622
576
  const stats = await indexer.indexCodebase(codebaseDir);
@@ -631,7 +585,7 @@ function validate(): boolean {
631
585
  await createTestFile(
632
586
  codebaseDir,
633
587
  "test.ts",
634
- "export const testData = true;\nconsole.log('Test data loaded');",
588
+ "export const testData = true;\nconsole.log('Test data loaded');"
635
589
  );
636
590
 
637
591
  const stats1 = await indexer.indexCodebase(codebaseDir);
@@ -683,7 +637,7 @@ function validate(): boolean {
683
637
  await createTestFile(
684
638
  codebaseDir,
685
639
  `component${i}.ts`,
686
- `export class Component${i} {\n private value = ${i};\n render() {\n console.log('Rendering component ${i}');\n return this.value;\n }\n}`,
640
+ `export class Component${i} {\n private value = ${i};\n render() {\n console.log('Rendering component ${i}');\n return this.value;\n }\n}`
687
641
  );
688
642
  }
689
643
 
@@ -710,7 +664,7 @@ function validate(): boolean {
710
664
  await createTestFile(
711
665
  codebaseDir,
712
666
  "timestamped.ts",
713
- "export const timestamp = Date.now();\nconsole.log('Timestamp test');\nfunction getTime() { return timestamp; }",
667
+ "export const timestamp = Date.now();\nconsole.log('Timestamp test');\nfunction getTime() { return timestamp; }"
714
668
  );
715
669
 
716
670
  const beforeIndexing = new Date();
@@ -722,12 +676,8 @@ function validate(): boolean {
722
676
  expect(status.status).toBe("indexed");
723
677
  expect(status.lastUpdated).toBeDefined();
724
678
  expect(status.lastUpdated).toBeInstanceOf(Date);
725
- expect(status.lastUpdated!.getTime()).toBeGreaterThanOrEqual(
726
- beforeIndexing.getTime(),
727
- );
728
- expect(status.lastUpdated!.getTime()).toBeLessThanOrEqual(
729
- afterIndexing.getTime(),
730
- );
679
+ expect(status.lastUpdated?.getTime()).toBeGreaterThanOrEqual(beforeIndexing.getTime());
680
+ expect(status.lastUpdated?.getTime()).toBeLessThanOrEqual(afterIndexing.getTime());
731
681
  });
732
682
 
733
683
  it("should correctly count chunks excluding metadata point", async () => {
@@ -736,11 +686,11 @@ function validate(): boolean {
736
686
  await createTestFile(
737
687
  codebaseDir,
738
688
  `service${i}.ts`,
739
- `export class Service${i} {\n async process(input: string): Promise<string> {\n console.log('Processing in service ${i}:', input);\n const result = input.toUpperCase();\n return result;\n }\n async validate(data: any): Promise<boolean> {\n console.log('Validating in service ${i}');\n return data !== null;\n }\n}`,
689
+ `export class Service${i} {\n async process(input: string): Promise<string> {\n console.log('Processing in service ${i}:', input);\n const result = input.toUpperCase();\n return result;\n }\n async validate(data: any): Promise<boolean> {\n console.log('Validating in service ${i}');\n return data !== null;\n }\n}`
740
690
  );
741
691
  }
742
692
 
743
- const stats = await indexer.indexCodebase(codebaseDir);
693
+ const _stats = await indexer.indexCodebase(codebaseDir);
744
694
  const status = await indexer.getIndexStatus(codebaseDir);
745
695
 
746
696
  // The chunks count in status should match what was indexed
@@ -755,7 +705,7 @@ function validate(): boolean {
755
705
  await createTestFile(
756
706
  codebaseDir,
757
707
  "reindexable.ts",
758
- "export const version = 1;\nconsole.log('Version:', version);\nfunction getVersion() { return version; }",
708
+ "export const version = 1;\nconsole.log('Version:', version);\nfunction getVersion() { return version; }"
759
709
  );
760
710
 
761
711
  // Initial index
@@ -777,9 +727,7 @@ function validate(): boolean {
777
727
 
778
728
  // Timestamp should be updated
779
729
  if (firstTimestamp && status.lastUpdated) {
780
- expect(status.lastUpdated.getTime()).toBeGreaterThanOrEqual(
781
- firstTimestamp.getTime(),
782
- );
730
+ expect(status.lastUpdated.getTime()).toBeGreaterThanOrEqual(firstTimestamp.getTime());
783
731
  }
784
732
  });
785
733
  });
@@ -790,7 +738,7 @@ function validate(): boolean {
790
738
  await createTestFile(
791
739
  codebaseDir,
792
740
  `file${i}.ts`,
793
- `export const value${i} = ${i};\nconsole.log('File ${i} loaded successfully');\nfunction process${i}() { return value${i} * 2; }`,
741
+ `export const value${i} = ${i};\nconsole.log('File ${i} loaded successfully');\nfunction process${i}() { return value${i} * 2; }`
794
742
  );
795
743
  }
796
744
 
@@ -811,14 +759,14 @@ function validate(): boolean {
811
759
  await createTestFile(
812
760
  codebaseDir,
813
761
  "file1.ts",
814
- "export const initial = 1;\nconsole.log('Initial file');",
762
+ "export const initial = 1;\nconsole.log('Initial file');"
815
763
  );
816
764
  await indexer.indexCodebase(codebaseDir);
817
765
 
818
766
  await createTestFile(
819
767
  codebaseDir,
820
768
  "file2.ts",
821
- "export const additional = 2;\nconsole.log('Additional file');",
769
+ "export const additional = 2;\nconsole.log('Additional file');"
822
770
  );
823
771
 
824
772
  const progressUpdates: string[] = [];
@@ -835,17 +783,13 @@ function validate(): boolean {
835
783
  describe("Hybrid search with incremental updates", () => {
836
784
  it("should use hybrid search during reindexChanges", async () => {
837
785
  const hybridConfig = { ...config, enableHybridSearch: true };
838
- const hybridIndexer = new CodeIndexer(
839
- qdrant as any,
840
- embeddings,
841
- hybridConfig,
842
- );
786
+ const hybridIndexer = new CodeIndexer(qdrant as any, embeddings, hybridConfig);
843
787
 
844
788
  // Initial indexing with hybrid search
845
789
  await createTestFile(
846
790
  codebaseDir,
847
791
  "initial.ts",
848
- "export const initial = 1;\nconsole.log('Initial file');",
792
+ "export const initial = 1;\nconsole.log('Initial file');"
849
793
  );
850
794
  await hybridIndexer.indexCodebase(codebaseDir);
851
795
 
@@ -869,7 +813,7 @@ export class DataProcessor {
869
813
  process(input: string): string {
870
814
  return input.trim();
871
815
  }
872
- }`,
816
+ }`
873
817
  );
874
818
 
875
819
  // Reindex with hybrid search - this should cover lines 540-545
@@ -886,7 +830,7 @@ export class DataProcessor {
886
830
  await createTestFile(
887
831
  codebaseDir,
888
832
  "file1.ts",
889
- "export const value = 1;\nconsole.log('File 1');",
833
+ "export const value = 1;\nconsole.log('File 1');"
890
834
  );
891
835
  await indexer.indexCodebase(codebaseDir);
892
836
 
@@ -894,7 +838,7 @@ export class DataProcessor {
894
838
  await createTestFile(
895
839
  codebaseDir,
896
840
  "file2.ts",
897
- "export const value2 = 2;\nconsole.log('File 2');",
841
+ "export const value2 = 2;\nconsole.log('File 2');"
898
842
  );
899
843
 
900
844
  // This should not throw even if there are processing errors
@@ -911,7 +855,7 @@ export class DataProcessor {
911
855
  async function createTestFile(
912
856
  baseDir: string,
913
857
  relativePath: string,
914
- content: string,
858
+ content: string
915
859
  ): Promise<void> {
916
860
  const fullPath = join(baseDir, relativePath);
917
861
  const dir = join(fullPath, "..");
@@ -41,9 +41,7 @@ describe("FileScanner", () => {
41
41
  it("should respect supported extensions", async () => {
42
42
  const files = await scanner.scanDirectory(join(fixturesDir, "sample-ts"));
43
43
  files.forEach((file) => {
44
- const hasValidExt = config.supportedExtensions.some((ext) =>
45
- file.endsWith(ext),
46
- );
44
+ const hasValidExt = config.supportedExtensions.some((ext) => file.endsWith(ext));
47
45
  expect(hasValidExt).toBe(true);
48
46
  });
49
47
  });
@@ -69,9 +67,7 @@ describe("FileScanner", () => {
69
67
  });
70
68
 
71
69
  it("should handle missing ignore files gracefully", async () => {
72
- await expect(
73
- scanner.loadIgnorePatterns("/nonexistent/path"),
74
- ).resolves.not.toThrow();
70
+ await expect(scanner.loadIgnorePatterns("/nonexistent/path")).resolves.not.toThrow();
75
71
  });
76
72
  });
77
73
 
@@ -92,12 +88,7 @@ describe("FileScanner", () => {
92
88
  await ignoreScanner.loadIgnorePatterns(join(fixturesDir, "sample-ts"));
93
89
 
94
90
  const rootPath = join(fixturesDir, "sample-ts");
95
- const ignoredPath = join(
96
- rootPath,
97
- "node_modules",
98
- "some-package",
99
- "index.js",
100
- );
91
+ const ignoredPath = join(rootPath, "node_modules", "some-package", "index.js");
101
92
 
102
93
  expect(ignoreScanner.shouldIgnore(ignoredPath, rootPath)).toBe(true);
103
94
  });
@@ -127,21 +118,11 @@ describe("FileScanner", () => {
127
118
 
128
119
  const rootPath = join(fixturesDir, "sample-ts");
129
120
 
130
- expect(
131
- customScanner.shouldIgnore(
132
- join(rootPath, "src", "utils.test.ts"),
133
- rootPath,
134
- ),
135
- ).toBe(true);
136
- expect(
137
- customScanner.shouldIgnore(
138
- join(rootPath, "tests", "main.ts"),
139
- rootPath,
140
- ),
141
- ).toBe(true);
142
- expect(
143
- customScanner.shouldIgnore(join(rootPath, "src", "utils.ts"), rootPath),
144
- ).toBe(false);
121
+ expect(customScanner.shouldIgnore(join(rootPath, "src", "utils.test.ts"), rootPath)).toBe(
122
+ true
123
+ );
124
+ expect(customScanner.shouldIgnore(join(rootPath, "tests", "main.ts"), rootPath)).toBe(true);
125
+ expect(customScanner.shouldIgnore(join(rootPath, "src", "utils.ts"), rootPath)).toBe(false);
145
126
  });
146
127
  });
147
128
 
@@ -164,9 +145,7 @@ describe("FileScanner", () => {
164
145
  };
165
146
  const customScanner = new FileScanner(customConfig);
166
147
  await customScanner.loadIgnorePatterns(join(fixturesDir, "sample-ts"));
167
- const files = await customScanner.scanDirectory(
168
- join(fixturesDir, "sample-ts"),
169
- );
148
+ const files = await customScanner.scanDirectory(join(fixturesDir, "sample-ts"));
170
149
  expect(files.some((f) => f.includes(".test.ts"))).toBe(false);
171
150
  });
172
151
 
@@ -177,9 +156,7 @@ describe("FileScanner", () => {
177
156
  };
178
157
  const ignoreScanner = new FileScanner(ignoreConfig);
179
158
  await ignoreScanner.loadIgnorePatterns(join(fixturesDir, "sample-ts"));
180
- const files = await ignoreScanner.scanDirectory(
181
- join(fixturesDir, "sample-ts"),
182
- );
159
+ const files = await ignoreScanner.scanDirectory(join(fixturesDir, "sample-ts"));
183
160
 
184
161
  // Should not include auth.ts due to ignore pattern
185
162
  expect(files.some((f) => f.endsWith("auth.ts"))).toBe(false);
@@ -187,12 +164,8 @@ describe("FileScanner", () => {
187
164
 
188
165
  it("should handle directories with .gitignore", async () => {
189
166
  const scannerWithGitignore = new FileScanner(config);
190
- await scannerWithGitignore.loadIgnorePatterns(
191
- join(fixturesDir, "sample-ts"),
192
- );
193
- const files = await scannerWithGitignore.scanDirectory(
194
- join(fixturesDir, "sample-ts"),
195
- );
167
+ await scannerWithGitignore.loadIgnorePatterns(join(fixturesDir, "sample-ts"));
168
+ const files = await scannerWithGitignore.scanDirectory(join(fixturesDir, "sample-ts"));
196
169
 
197
170
  // Files matching .gitignore patterns should be excluded
198
171
  expect(Array.isArray(files)).toBe(true);
@@ -14,7 +14,7 @@ describe("SnapshotManager", () => {
14
14
  // Create a temporary directory for test snapshots
15
15
  tempDir = join(
16
16
  tmpdir(),
17
- `qdrant-mcp-test-${Date.now()}-${Math.random().toString(36).substring(7)}`,
17
+ `qdrant-mcp-test-${Date.now()}-${Math.random().toString(36).substring(7)}`
18
18
  );
19
19
  await fs.mkdir(tempDir, { recursive: true });
20
20
 
@@ -177,11 +177,7 @@ describe("SnapshotManager", () => {
177
177
 
178
178
  it("should handle missing fields in snapshot", async () => {
179
179
  const snapshotPath = join(tempDir, `${collectionName}.json`);
180
- await fs.writeFile(
181
- snapshotPath,
182
- JSON.stringify({ codebasePath: "/test" }),
183
- "utf-8",
184
- );
180
+ await fs.writeFile(snapshotPath, JSON.stringify({ codebasePath: "/test" }), "utf-8");
185
181
 
186
182
  const loaded = await snapshotManager.load();
187
183
 
@@ -376,9 +372,7 @@ describe("SnapshotManager", () => {
376
372
  const tree = new MerkleTree();
377
373
  tree.build(fileHashes);
378
374
 
379
- promises.push(
380
- snapshotManager.save(`/test/codebase${i}`, fileHashes, tree),
381
- );
375
+ promises.push(snapshotManager.save(`/test/codebase${i}`, fileHashes, tree));
382
376
  }
383
377
 
384
378
  await Promise.all(promises);
@@ -395,11 +389,7 @@ describe("SnapshotManager", () => {
395
389
 
396
390
  await snapshotManager.save("/test/codebase", fileHashes, tree);
397
391
 
398
- const promises = [
399
- snapshotManager.load(),
400
- snapshotManager.load(),
401
- snapshotManager.load(),
402
- ];
392
+ const promises = [snapshotManager.load(), snapshotManager.load(), snapshotManager.load()];
403
393
 
404
394
  const results = await Promise.all(promises);
405
395