@cogitator-ai/memory 0.6.1 → 0.6.2
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.
- package/README.md +106 -0
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -20,7 +20,9 @@ pnpm add pg # For PostgreSQL adapter
|
|
|
20
20
|
- **Context Builder** - Build token-aware conversation context
|
|
21
21
|
- **Embedding Services** - OpenAI and Ollama embedding integration
|
|
22
22
|
- **Semantic Search** - Vector similarity search with pgvector
|
|
23
|
+
- **Hybrid Search** - BM25 + Vector with Reciprocal Rank Fusion
|
|
23
24
|
- **Facts Storage** - Store and retrieve agent knowledge
|
|
25
|
+
- **Knowledge Graph** - Entity-relationship memory with multi-hop traversal
|
|
24
26
|
- **Zod Schemas** - Type-safe configuration validation
|
|
25
27
|
|
|
26
28
|
---
|
|
@@ -356,6 +358,110 @@ const vector = await embeddings.embed('Hello, world!');
|
|
|
356
358
|
|
|
357
359
|
---
|
|
358
360
|
|
|
361
|
+
## Hybrid Search
|
|
362
|
+
|
|
363
|
+
Combine keyword search (BM25) with semantic search (vector embeddings) using Reciprocal Rank Fusion for best-of-both-worlds retrieval.
|
|
364
|
+
|
|
365
|
+
### Configuration
|
|
366
|
+
|
|
367
|
+
```typescript
|
|
368
|
+
import {
|
|
369
|
+
HybridSearch,
|
|
370
|
+
InMemoryEmbeddingAdapter,
|
|
371
|
+
OpenAIEmbeddingService,
|
|
372
|
+
} from '@cogitator-ai/memory';
|
|
373
|
+
|
|
374
|
+
const embeddingService = new OpenAIEmbeddingService({
|
|
375
|
+
apiKey: process.env.OPENAI_API_KEY!,
|
|
376
|
+
});
|
|
377
|
+
|
|
378
|
+
const embeddingAdapter = new InMemoryEmbeddingAdapter();
|
|
379
|
+
|
|
380
|
+
const search = new HybridSearch({
|
|
381
|
+
embeddingAdapter,
|
|
382
|
+
embeddingService,
|
|
383
|
+
keywordAdapter: embeddingAdapter, // PostgresAdapter also implements KeywordSearchAdapter
|
|
384
|
+
defaultWeights: { bm25: 0.4, vector: 0.6 },
|
|
385
|
+
});
|
|
386
|
+
```
|
|
387
|
+
|
|
388
|
+
### Search Strategies
|
|
389
|
+
|
|
390
|
+
```typescript
|
|
391
|
+
// Pure vector search (semantic similarity)
|
|
392
|
+
const vectorResults = await search.search({
|
|
393
|
+
query: 'machine learning algorithms',
|
|
394
|
+
strategy: 'vector',
|
|
395
|
+
limit: 10,
|
|
396
|
+
});
|
|
397
|
+
|
|
398
|
+
// Pure keyword search (BM25)
|
|
399
|
+
const keywordResults = await search.search({
|
|
400
|
+
query: 'machine learning algorithms',
|
|
401
|
+
strategy: 'keyword',
|
|
402
|
+
limit: 10,
|
|
403
|
+
});
|
|
404
|
+
|
|
405
|
+
// Hybrid search (combines both with RRF)
|
|
406
|
+
const hybridResults = await search.search({
|
|
407
|
+
query: 'machine learning algorithms',
|
|
408
|
+
strategy: 'hybrid',
|
|
409
|
+
weights: { bm25: 0.4, vector: 0.6 },
|
|
410
|
+
limit: 10,
|
|
411
|
+
});
|
|
412
|
+
|
|
413
|
+
// Results include both scores
|
|
414
|
+
hybridResults.data.forEach((result) => {
|
|
415
|
+
console.log(`${result.content} — score: ${result.score}`);
|
|
416
|
+
console.log(` vector: ${result.vectorScore}, keyword: ${result.keywordScore}`);
|
|
417
|
+
});
|
|
418
|
+
```
|
|
419
|
+
|
|
420
|
+
### Document Indexing
|
|
421
|
+
|
|
422
|
+
For keyword search, documents must be indexed:
|
|
423
|
+
|
|
424
|
+
```typescript
|
|
425
|
+
// Add documents to BM25 index
|
|
426
|
+
search.indexDocument('doc-1', 'Machine learning is a subset of AI...');
|
|
427
|
+
search.indexDocument('doc-2', 'Deep learning uses neural networks...');
|
|
428
|
+
|
|
429
|
+
// Remove from index
|
|
430
|
+
search.removeDocument('doc-1');
|
|
431
|
+
|
|
432
|
+
// Clear entire index
|
|
433
|
+
search.clearIndex();
|
|
434
|
+
|
|
435
|
+
// Check index size
|
|
436
|
+
console.log('Indexed documents:', search.indexSize);
|
|
437
|
+
```
|
|
438
|
+
|
|
439
|
+
### Why Hybrid Search?
|
|
440
|
+
|
|
441
|
+
| Search Type | Strengths | Weaknesses |
|
|
442
|
+
| ------------------ | ---------------------------------------------------- | ------------------------------- |
|
|
443
|
+
| **Vector** | Finds semantically similar content, handles synonyms | Misses exact keyword matches |
|
|
444
|
+
| **Keyword (BM25)** | Exact term matching, fast | Misses synonyms and paraphrases |
|
|
445
|
+
| **Hybrid** | Best of both worlds | Slightly more computation |
|
|
446
|
+
|
|
447
|
+
**Example:** Query "ML algorithms"
|
|
448
|
+
|
|
449
|
+
- Vector search finds "machine learning methods" (semantic match)
|
|
450
|
+
- Keyword search finds "ML algorithms comparison" (exact match)
|
|
451
|
+
- Hybrid returns both, ranked by combined relevance
|
|
452
|
+
|
|
453
|
+
### Reciprocal Rank Fusion (RRF)
|
|
454
|
+
|
|
455
|
+
Hybrid search uses RRF to combine rankings from both search methods:
|
|
456
|
+
|
|
457
|
+
```
|
|
458
|
+
RRF_score(d) = Σ 1 / (k + rank_i(d))
|
|
459
|
+
```
|
|
460
|
+
|
|
461
|
+
Where `k` is a constant (default 60) and `rank_i(d)` is the rank of document `d` in result set `i`. This produces stable rankings even when individual scores are on different scales.
|
|
462
|
+
|
|
463
|
+
---
|
|
464
|
+
|
|
359
465
|
## Zod Schemas
|
|
360
466
|
|
|
361
467
|
Type-safe configuration validation:
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cogitator-ai/memory",
|
|
3
|
-
"version": "0.6.
|
|
3
|
+
"version": "0.6.2",
|
|
4
4
|
"description": "Memory adapters for Cogitator AI agents",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -19,8 +19,8 @@
|
|
|
19
19
|
"@types/pg": "^8.10.9",
|
|
20
20
|
"nanoid": "^5.0.4",
|
|
21
21
|
"zod": "^3.22.4",
|
|
22
|
-
"@cogitator-ai/
|
|
23
|
-
"@cogitator-ai/
|
|
22
|
+
"@cogitator-ai/types": "0.12.0",
|
|
23
|
+
"@cogitator-ai/redis": "0.2.11"
|
|
24
24
|
},
|
|
25
25
|
"optionalDependencies": {
|
|
26
26
|
"ioredis": "^5.3.2",
|