aether-core 0.1.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.
@@ -0,0 +1,880 @@
1
+ /**
2
+ * Represents a relationship between memory events.
3
+ */
4
+ interface EventRelation {
5
+ /** The type of relationship */
6
+ type: 'follows' | 'references' | 'causes' | 'related_to';
7
+ /** The ID of the target event */
8
+ targetEventId: string;
9
+ /** Optional metadata about the relationship */
10
+ metadata?: Record<string, unknown>;
11
+ }
12
+ /**
13
+ * Core data model for a memory event.
14
+ * All memories are stored as structured events, ensuring temporal
15
+ * and relational context is preserved.
16
+ */
17
+ interface MemoryEvent {
18
+ /** Unique identifier for the memory event (ULID for sortability) */
19
+ id: string;
20
+ /** ISO 8601 timestamp of when the event occurred */
21
+ timestamp: string;
22
+ /** Entity that performed the action (e.g., 'user123', 'system', 'assistant') */
23
+ actor: string;
24
+ /** Type of action or event (e.g., 'selected', 'purchased', 'responded') */
25
+ action: string;
26
+ /** Natural language description of the event */
27
+ content: string;
28
+ /** Structured metadata providing context */
29
+ context: Record<string, unknown>;
30
+ /** Vector embedding for semantic search (added by the system) */
31
+ embedding?: number[];
32
+ /** Optional relations to other events */
33
+ relations?: EventRelation[];
34
+ }
35
+ /**
36
+ * Input for creating a new memory event.
37
+ * Most fields are optional and will be auto-populated.
38
+ */
39
+ interface MemoryEventInput {
40
+ /** Entity that performed the action */
41
+ actor?: string;
42
+ /** Type of action or event */
43
+ action?: string;
44
+ /** Natural language description of the event (required) */
45
+ content: string;
46
+ /** Structured metadata providing context */
47
+ context?: Record<string, unknown>;
48
+ /** Optional relations to other events */
49
+ relations?: EventRelation[];
50
+ }
51
+ /**
52
+ * A memory event with an associated relevance score.
53
+ * Used in retrieval results.
54
+ */
55
+ interface ScoredMemoryEvent extends MemoryEvent {
56
+ /** Relevance score (0-1, higher is more relevant) */
57
+ score: number;
58
+ }
59
+
60
+ /**
61
+ * Time range for filtering events.
62
+ */
63
+ interface TimeRange {
64
+ /** Start of the time range (ISO 8601) */
65
+ start: string;
66
+ /** End of the time range (ISO 8601) */
67
+ end: string;
68
+ }
69
+ /**
70
+ * Retrieval strategy type.
71
+ */
72
+ type RetrievalType = 'semantic' | 'temporal' | 'relational' | 'hybrid';
73
+ /**
74
+ * Options for retrieving memories.
75
+ */
76
+ interface RetrievalOptions {
77
+ /** Filter by actor */
78
+ actor?: string;
79
+ /** Filter by time range */
80
+ timeRange?: TimeRange;
81
+ /** Maximum number of results to return */
82
+ limit?: number;
83
+ /** Type of retrieval strategy to use */
84
+ retrievalType?: RetrievalType;
85
+ /** Filter by specific context fields */
86
+ contextFilters?: Record<string, unknown>;
87
+ /** Include embedding vectors in results */
88
+ includeEmbeddings?: boolean;
89
+ /** Minimum similarity threshold for semantic search (0-1) */
90
+ threshold?: number;
91
+ }
92
+ /**
93
+ * Options for advanced multi-modal search.
94
+ */
95
+ interface AdvancedSearchOptions {
96
+ /** Semantic search configuration */
97
+ semantic?: {
98
+ /** Query text for semantic similarity */
99
+ query: string;
100
+ /** Weight for this retrieval mode (0-1) */
101
+ weight?: number;
102
+ };
103
+ /** Temporal search configuration */
104
+ temporal?: {
105
+ /** Actor to retrieve history for */
106
+ actor: string;
107
+ /** How many recent events to consider */
108
+ recency?: number;
109
+ /** Weight for this retrieval mode (0-1) */
110
+ weight?: number;
111
+ };
112
+ /** Relational search configuration */
113
+ relational?: {
114
+ /** Context keys to match */
115
+ contextKeys: string[];
116
+ /** Values to match */
117
+ values: unknown[];
118
+ /** Weight for this retrieval mode (0-1) */
119
+ weight?: number;
120
+ };
121
+ /** Maximum number of results */
122
+ limit?: number;
123
+ /** How to combine results from different strategies */
124
+ combineStrategy?: 'union' | 'intersection' | 'weighted';
125
+ }
126
+ /**
127
+ * Options for querying by actor.
128
+ */
129
+ interface TemporalQueryOptions {
130
+ /** Maximum number of results */
131
+ limit?: number;
132
+ /** Offset for pagination */
133
+ offset?: number;
134
+ /** Sort order by timestamp */
135
+ order?: 'asc' | 'desc';
136
+ }
137
+ /**
138
+ * General query options.
139
+ */
140
+ interface QueryOptions {
141
+ /** Maximum number of results */
142
+ limit?: number;
143
+ /** Offset for pagination */
144
+ offset?: number;
145
+ }
146
+ /**
147
+ * Options for vector similarity search.
148
+ */
149
+ interface VectorSearchOptions {
150
+ /** Maximum number of results */
151
+ limit?: number;
152
+ /** Minimum similarity threshold (0-1) */
153
+ threshold?: number;
154
+ /** Additional filters to apply */
155
+ filters?: Record<string, unknown>;
156
+ }
157
+
158
+ /**
159
+ * Abstract interface for storage adapters.
160
+ * Implementations can use any backing store (in-memory, PostgreSQL, Neo4j, etc.)
161
+ */
162
+ interface StorageAdapter {
163
+ /** Unique identifier for this adapter type */
164
+ readonly name: string;
165
+ /**
166
+ * Initialize the adapter (create tables, indexes, etc.)
167
+ * Called once before any other operations.
168
+ */
169
+ initialize(): Promise<void>;
170
+ /**
171
+ * Store a single memory event.
172
+ * @param event The event to store (must include id and embedding if applicable)
173
+ * @returns The stored event
174
+ */
175
+ store(event: MemoryEvent): Promise<MemoryEvent>;
176
+ /**
177
+ * Store multiple memory events in a batch.
178
+ * @param events The events to store
179
+ * @returns The stored events
180
+ */
181
+ storeBatch(events: MemoryEvent[]): Promise<MemoryEvent[]>;
182
+ /**
183
+ * Retrieve an event by its ID.
184
+ * @param id The event ID
185
+ * @returns The event or null if not found
186
+ */
187
+ getById(id: string): Promise<MemoryEvent | null>;
188
+ /**
189
+ * Retrieve multiple events by their IDs.
190
+ * @param ids The event IDs
191
+ * @returns The found events (may be fewer than requested)
192
+ */
193
+ getByIds(ids: string[]): Promise<MemoryEvent[]>;
194
+ /**
195
+ * Query events by actor (for temporal retrieval).
196
+ * @param actor The actor identifier
197
+ * @param options Query options (limit, offset, order)
198
+ * @returns Events for the actor, ordered by timestamp
199
+ */
200
+ queryByActor(actor: string, options?: TemporalQueryOptions): Promise<MemoryEvent[]>;
201
+ /**
202
+ * Query events by context fields (for relational retrieval).
203
+ * @param filters Key-value pairs to match in event context
204
+ * @param options Query options
205
+ * @returns Matching events
206
+ */
207
+ queryByContext(filters: Record<string, unknown>, options?: QueryOptions): Promise<MemoryEvent[]>;
208
+ /**
209
+ * Query events within a time range.
210
+ * @param range The time range (start/end ISO 8601)
211
+ * @param options Query options
212
+ * @returns Events within the range
213
+ */
214
+ queryByTimeRange(range: TimeRange, options?: QueryOptions): Promise<MemoryEvent[]>;
215
+ /**
216
+ * Search for events by vector similarity (for semantic retrieval).
217
+ * @param vector The query embedding vector
218
+ * @param options Search options (limit, threshold, filters)
219
+ * @returns Scored events, ordered by similarity (highest first)
220
+ */
221
+ searchByVector(vector: number[], options?: VectorSearchOptions): Promise<ScoredMemoryEvent[]>;
222
+ /**
223
+ * Delete an event by ID.
224
+ * @param id The event ID to delete
225
+ * @returns True if deleted, false if not found
226
+ */
227
+ delete(id: string): Promise<boolean>;
228
+ /**
229
+ * Delete multiple events by IDs.
230
+ * @param ids The event IDs to delete
231
+ * @returns Number of events deleted
232
+ */
233
+ deleteBatch(ids: string[]): Promise<number>;
234
+ /**
235
+ * Delete all events. Use with caution!
236
+ */
237
+ clear(): Promise<void>;
238
+ /**
239
+ * Get the count of stored events.
240
+ * @param filters Optional filters to count specific events
241
+ * @returns The event count
242
+ */
243
+ count(filters?: Record<string, unknown>): Promise<number>;
244
+ /**
245
+ * Get all unique actors.
246
+ * @returns Array of actor identifiers
247
+ */
248
+ getActors(): Promise<string[]>;
249
+ /**
250
+ * Close connections and cleanup resources.
251
+ */
252
+ close(): Promise<void>;
253
+ }
254
+
255
+ /**
256
+ * Abstract interface for embedding providers.
257
+ * Implementations can use any embedding service (VoyageAI, OpenAI, local models, etc.)
258
+ */
259
+ interface EmbeddingProvider {
260
+ /** Unique identifier for this provider */
261
+ readonly name: string;
262
+ /** Number of dimensions in the embedding vectors */
263
+ readonly dimensions: number;
264
+ /**
265
+ * Generate an embedding vector for a single text.
266
+ * @param text The text to embed
267
+ * @returns The embedding vector
268
+ */
269
+ embed(text: string): Promise<number[]>;
270
+ /**
271
+ * Generate embedding vectors for multiple texts.
272
+ * More efficient than calling embed() multiple times.
273
+ * @param texts The texts to embed
274
+ * @returns Array of embedding vectors (same order as input)
275
+ */
276
+ embedBatch(texts: string[]): Promise<number[][]>;
277
+ /**
278
+ * Calculate the similarity between two embedding vectors.
279
+ * @param a First embedding vector
280
+ * @param b Second embedding vector
281
+ * @returns Similarity score (typically 0-1 for normalized vectors)
282
+ */
283
+ similarity(a: number[], b: number[]): number;
284
+ }
285
+
286
+ /**
287
+ * Configuration for the storage layer.
288
+ */
289
+ interface StorageConfig {
290
+ /** The storage adapter instance */
291
+ adapter: StorageAdapter;
292
+ }
293
+ /**
294
+ * Configuration for the embedding provider.
295
+ */
296
+ interface EmbeddingConfig {
297
+ /** The embedding provider instance */
298
+ provider: EmbeddingProvider;
299
+ /** Model to use (provider-specific) */
300
+ model?: string;
301
+ /** Embedding dimensions (auto-detected from provider if not specified) */
302
+ dimensions?: number;
303
+ /** Batch size for embedding multiple texts */
304
+ batchSize?: number;
305
+ }
306
+ /**
307
+ * Configuration for retrieval behavior.
308
+ */
309
+ interface RetrievalConfig {
310
+ /** Default maximum number of results */
311
+ defaultLimit?: number;
312
+ /** Default retrieval type */
313
+ defaultType?: RetrievalType;
314
+ /** Weights for hybrid retrieval (must sum to 1) */
315
+ hybridWeights?: {
316
+ semantic: number;
317
+ temporal: number;
318
+ relational: number;
319
+ };
320
+ /** Reranker configuration */
321
+ reranker?: RerankerConfig;
322
+ }
323
+ /**
324
+ * Configuration for result reranking.
325
+ */
326
+ interface RerankerConfig {
327
+ /** Whether reranking is enabled */
328
+ enabled: boolean;
329
+ /** Model to use for reranking (if applicable) */
330
+ model?: string;
331
+ /** Number of results to rerank */
332
+ topK?: number;
333
+ }
334
+ /**
335
+ * Logging configuration.
336
+ */
337
+ interface LoggingConfig {
338
+ /** Log level */
339
+ level: 'debug' | 'info' | 'warn' | 'error';
340
+ /** Where to send logs */
341
+ destination?: 'console' | 'file' | 'custom';
342
+ /** Custom log handler */
343
+ handler?: (level: string, message: string, data?: unknown) => void;
344
+ }
345
+ /**
346
+ * Main configuration for Aether.
347
+ */
348
+ interface AetherConfig {
349
+ /** Storage configuration */
350
+ storage: StorageConfig;
351
+ /** Embedding configuration */
352
+ embeddings: EmbeddingConfig;
353
+ /** Retrieval configuration (optional) */
354
+ retrieval?: RetrievalConfig;
355
+ /** Logging configuration (optional) */
356
+ logging?: LoggingConfig;
357
+ }
358
+ /**
359
+ * Statistics about the memory store.
360
+ */
361
+ interface MemoryStats {
362
+ /** Total number of events stored */
363
+ totalEvents: number;
364
+ /** Number of unique actors */
365
+ uniqueActors: number;
366
+ /** Timestamp of oldest event */
367
+ oldestEvent?: string;
368
+ /** Timestamp of newest event */
369
+ newestEvent?: string;
370
+ /** Name of the storage adapter */
371
+ storageAdapter: string;
372
+ /** Name of the embedding provider */
373
+ embeddingProvider: string;
374
+ }
375
+
376
+ /**
377
+ * Type for unsubscribe function returned by subscribe.
378
+ */
379
+ type Unsubscribe = () => void;
380
+ /**
381
+ * Event listener callback type.
382
+ */
383
+ type EventListener = (event: MemoryEvent) => void;
384
+ /**
385
+ * Aether - Event-driven memory framework for LLM/AI agents.
386
+ *
387
+ * Provides a simple, intuitive API for recording and retrieving memories,
388
+ * moving beyond the limitations of pure vector-based RAG.
389
+ *
390
+ * @example
391
+ * ```typescript
392
+ * const aether = new Aether({
393
+ * storage: { adapter: new InMemoryStorageAdapter() },
394
+ * embeddings: { provider: new VoyageProvider({ apiKey: '...' }) },
395
+ * });
396
+ *
397
+ * // Add a memory
398
+ * await aether.add('User selected product XYZ', { productId: 'xyz' });
399
+ *
400
+ * // Retrieve relevant memories
401
+ * const memories = await aether.retrieve('What did the user look at?');
402
+ * ```
403
+ */
404
+ declare class Aether {
405
+ private readonly storage;
406
+ private readonly embeddings;
407
+ private readonly retrieval;
408
+ private readonly config;
409
+ private readonly listeners;
410
+ private initialized;
411
+ constructor(config: AetherConfig);
412
+ /**
413
+ * Initialize the memory system.
414
+ * Called automatically on first operation if not called explicitly.
415
+ */
416
+ initialize(): Promise<void>;
417
+ /**
418
+ * Add a memory event.
419
+ *
420
+ * @example Simple string input
421
+ * ```typescript
422
+ * await aether.add('User clicked the buy button');
423
+ * ```
424
+ *
425
+ * @example With context
426
+ * ```typescript
427
+ * await aether.add('User added item to cart', { cartId: '123', itemId: 'xyz' });
428
+ * ```
429
+ *
430
+ * @example Structured input
431
+ * ```typescript
432
+ * await aether.add({
433
+ * actor: 'user123',
434
+ * action: 'purchase',
435
+ * content: 'Purchased premium subscription',
436
+ * context: { planId: 'premium', amount: 99.99 }
437
+ * });
438
+ * ```
439
+ */
440
+ add(content: string, context?: Record<string, unknown>): Promise<MemoryEvent>;
441
+ add(event: MemoryEventInput): Promise<MemoryEvent>;
442
+ /**
443
+ * Add multiple memory events in a batch.
444
+ * More efficient than calling add() multiple times.
445
+ */
446
+ addBatch(events: MemoryEventInput[]): Promise<MemoryEvent[]>;
447
+ /**
448
+ * Retrieve relevant memories based on a query.
449
+ * Uses multi-modal retrieval (semantic, temporal, relational).
450
+ *
451
+ * @example Basic retrieval
452
+ * ```typescript
453
+ * const memories = await aether.retrieve('What products did the user view?');
454
+ * ```
455
+ *
456
+ * @example With options
457
+ * ```typescript
458
+ * const memories = await aether.retrieve('recent actions', {
459
+ * actor: 'user123',
460
+ * retrievalType: 'temporal',
461
+ * limit: 10
462
+ * });
463
+ * ```
464
+ */
465
+ retrieve(query: string, options?: RetrievalOptions): Promise<MemoryEvent[]>;
466
+ /**
467
+ * Get the history of events for a specific actor.
468
+ * Events are returned in reverse chronological order (most recent first).
469
+ */
470
+ getHistory(actor: string, limit?: number): Promise<MemoryEvent[]>;
471
+ /**
472
+ * Get a specific event by ID.
473
+ */
474
+ get(id: string): Promise<MemoryEvent | null>;
475
+ /**
476
+ * Delete a specific event by ID.
477
+ */
478
+ delete(id: string): Promise<boolean>;
479
+ /**
480
+ * Advanced multi-modal search with fine-grained control.
481
+ */
482
+ search(options: AdvancedSearchOptions): Promise<MemoryEvent[]>;
483
+ /**
484
+ * Get events related to a specific event.
485
+ * Follows the relations defined on the event.
486
+ */
487
+ getRelated(eventId: string, depth?: number): Promise<MemoryEvent[]>;
488
+ /**
489
+ * Subscribe to new memory events.
490
+ * Returns an unsubscribe function.
491
+ */
492
+ subscribe(callback: EventListener): Unsubscribe;
493
+ /**
494
+ * Get statistics about the memory store.
495
+ */
496
+ stats(): Promise<MemoryStats>;
497
+ /**
498
+ * Close the memory system and release resources.
499
+ */
500
+ close(): Promise<void>;
501
+ /**
502
+ * Clear all stored memories.
503
+ * Use with caution!
504
+ */
505
+ clear(): Promise<void>;
506
+ /**
507
+ * Infer an action type from content.
508
+ */
509
+ private inferAction;
510
+ /**
511
+ * Notify all listeners of a new event.
512
+ */
513
+ private notifyListeners;
514
+ }
515
+
516
+ /**
517
+ * In-memory storage adapter for development and testing.
518
+ * Uses Maps for O(1) lookups and maintains indexes for efficient queries.
519
+ */
520
+ declare class InMemoryStorageAdapter implements StorageAdapter {
521
+ readonly name = "in-memory";
522
+ /** Primary storage: id -> event */
523
+ private events;
524
+ /** Actor index: actor -> Set<event ids> */
525
+ private actorIndex;
526
+ /** Context index: context key -> value -> Set<event ids> */
527
+ private contextIndex;
528
+ /** Timestamp index: sorted list of [timestamp, id] for range queries */
529
+ private timestampIndex;
530
+ initialize(): Promise<void>;
531
+ store(event: MemoryEvent): Promise<MemoryEvent>;
532
+ storeBatch(events: MemoryEvent[]): Promise<MemoryEvent[]>;
533
+ getById(id: string): Promise<MemoryEvent | null>;
534
+ getByIds(ids: string[]): Promise<MemoryEvent[]>;
535
+ queryByActor(actor: string, options?: TemporalQueryOptions): Promise<MemoryEvent[]>;
536
+ queryByContext(filters: Record<string, unknown>, options?: QueryOptions): Promise<MemoryEvent[]>;
537
+ queryByTimeRange(range: TimeRange, options?: QueryOptions): Promise<MemoryEvent[]>;
538
+ searchByVector(vector: number[], options?: VectorSearchOptions): Promise<ScoredMemoryEvent[]>;
539
+ delete(id: string): Promise<boolean>;
540
+ deleteBatch(ids: string[]): Promise<number>;
541
+ clear(): Promise<void>;
542
+ count(filters?: Record<string, unknown>): Promise<number>;
543
+ getActors(): Promise<string[]>;
544
+ close(): Promise<void>;
545
+ /**
546
+ * Binary search to find insertion point for a timestamp.
547
+ */
548
+ private binarySearchInsert;
549
+ }
550
+
551
+ /**
552
+ * Mock embedding provider for testing and development.
553
+ * Generates deterministic pseudo-random embeddings based on text hash.
554
+ */
555
+ declare class MockEmbeddingProvider implements EmbeddingProvider {
556
+ readonly name = "mock";
557
+ readonly dimensions: number;
558
+ constructor(dimensions?: number);
559
+ embed(text: string): Promise<number[]>;
560
+ embedBatch(texts: string[]): Promise<number[][]>;
561
+ similarity(a: number[], b: number[]): number;
562
+ /**
563
+ * Generate a deterministic vector from text hash.
564
+ * Same text always produces the same vector.
565
+ */
566
+ private hashToVector;
567
+ /**
568
+ * Simple string hash function.
569
+ */
570
+ private simpleHash;
571
+ }
572
+
573
+ /**
574
+ * VoyageAI provider configuration.
575
+ */
576
+ interface VoyageProviderConfig {
577
+ /** VoyageAI API key */
578
+ apiKey: string;
579
+ /** Model to use (default: 'voyage-2') */
580
+ model?: VoyageModel;
581
+ /** Base URL (default: 'https://api.voyageai.com/v1') */
582
+ baseUrl?: string;
583
+ /** Maximum texts per batch (default: 128) */
584
+ batchSize?: number;
585
+ /** Request timeout in ms (default: 30000) */
586
+ timeout?: number;
587
+ /** Maximum retries on failure (default: 3) */
588
+ maxRetries?: number;
589
+ }
590
+ /**
591
+ * Available VoyageAI models with their dimensions.
592
+ */
593
+ type VoyageModel = 'voyage-3' | 'voyage-3-lite' | 'voyage-code-3' | 'voyage-finance-2' | 'voyage-law-2' | 'voyage-code-2' | 'voyage-2' | 'voyage-large-2' | 'voyage-large-2-instruct';
594
+ /**
595
+ * VoyageAI embedding provider.
596
+ * Uses VoyageAI's API for generating high-quality embeddings.
597
+ */
598
+ declare class VoyageProvider implements EmbeddingProvider {
599
+ readonly name = "voyage";
600
+ readonly dimensions: number;
601
+ private readonly apiKey;
602
+ private readonly model;
603
+ private readonly baseUrl;
604
+ private readonly batchSize;
605
+ private readonly timeout;
606
+ private readonly maxRetries;
607
+ constructor(config: VoyageProviderConfig);
608
+ embed(text: string): Promise<number[]>;
609
+ embedBatch(texts: string[]): Promise<number[][]>;
610
+ similarity(a: number[], b: number[]): number;
611
+ /**
612
+ * Embed a batch of texts with retry logic.
613
+ */
614
+ private embedWithRetry;
615
+ /**
616
+ * Call the VoyageAI API.
617
+ */
618
+ private callApi;
619
+ private sleep;
620
+ }
621
+
622
+ /**
623
+ * Context passed to retrieval strategies.
624
+ */
625
+ interface RetrievalContext {
626
+ /** The storage adapter for querying events */
627
+ storage: StorageAdapter;
628
+ /** The embedding provider for vectorizing queries */
629
+ embeddings: EmbeddingProvider;
630
+ }
631
+ /**
632
+ * Interface for retrieval strategies.
633
+ * Each strategy implements a different approach to finding relevant memories.
634
+ */
635
+ interface RetrievalStrategy {
636
+ /** The type of retrieval this strategy implements */
637
+ readonly type: RetrievalType;
638
+ /**
639
+ * Retrieve relevant memories using this strategy.
640
+ * @param query The search query
641
+ * @param context Storage and embedding context
642
+ * @param options Retrieval options
643
+ * @returns Scored memory events
644
+ */
645
+ retrieve(query: string, context: RetrievalContext, options: RetrievalOptions): Promise<ScoredMemoryEvent[]>;
646
+ }
647
+
648
+ /**
649
+ * The retrieval engine orchestrates multi-modal memory retrieval.
650
+ * It manages different strategies and combines their results.
651
+ */
652
+ declare class RetrievalEngine {
653
+ private readonly storage;
654
+ private readonly embeddings;
655
+ private readonly config;
656
+ private readonly strategies;
657
+ constructor(storage: StorageAdapter, embeddings: EmbeddingProvider, config?: RetrievalConfig);
658
+ /**
659
+ * Retrieve relevant memories based on a query.
660
+ * @param query The search query
661
+ * @param options Retrieval options
662
+ * @returns Array of relevant memory events
663
+ */
664
+ retrieve(query: string, options?: RetrievalOptions): Promise<MemoryEvent[]>;
665
+ /**
666
+ * Get a specific retrieval strategy.
667
+ */
668
+ getStrategy(type: RetrievalType): RetrievalStrategy | undefined;
669
+ /**
670
+ * Register a custom retrieval strategy.
671
+ */
672
+ registerStrategy(type: string, strategy: RetrievalStrategy): void;
673
+ /**
674
+ * Rerank results (placeholder - can be extended with cross-encoder models).
675
+ */
676
+ private rerank;
677
+ }
678
+
679
+ /**
680
+ * Semantic retrieval strategy.
681
+ * Finds memories that are semantically similar to the query using vector search.
682
+ */
683
+ declare class SemanticStrategy implements RetrievalStrategy {
684
+ readonly type: "semantic";
685
+ retrieve(query: string, context: RetrievalContext, options: RetrievalOptions): Promise<ScoredMemoryEvent[]>;
686
+ }
687
+
688
+ /**
689
+ * Temporal retrieval strategy.
690
+ * Retrieves recent memories for an actor, scoring by recency.
691
+ */
692
+ declare class TemporalStrategy implements RetrievalStrategy {
693
+ readonly type: "temporal";
694
+ /** Decay rate for recency scoring (higher = faster decay) */
695
+ private readonly decayRate;
696
+ constructor(decayRate?: number);
697
+ retrieve(_query: string, context: RetrievalContext, options: RetrievalOptions): Promise<ScoredMemoryEvent[]>;
698
+ }
699
+
700
+ /**
701
+ * Interface for entity extraction from text.
702
+ * Implement this to create custom entity extractors (regex, NLP, LLM-based, etc.)
703
+ */
704
+ interface EntityExtractor {
705
+ /**
706
+ * Extract entities from query text.
707
+ * @param query The query text to extract entities from
708
+ * @returns Object with entity key-value pairs (e.g., { userId: '123', productId: 'abc' })
709
+ */
710
+ extract(query: string): Record<string, unknown> | Promise<Record<string, unknown>>;
711
+ }
712
+ /**
713
+ * Configuration for pattern-based entity extraction.
714
+ */
715
+ interface EntityPattern {
716
+ /** The context key to store the extracted value under */
717
+ key: string;
718
+ /** Regex pattern with a capture group for the value */
719
+ pattern: RegExp;
720
+ }
721
+ /**
722
+ * Default entity patterns for common use cases.
723
+ * These can be extended or replaced entirely.
724
+ */
725
+ declare const DEFAULT_ENTITY_PATTERNS: EntityPattern[];
726
+ /**
727
+ * Pattern-based entity extractor.
728
+ * Uses regex patterns to extract entities from text.
729
+ */
730
+ declare class PatternEntityExtractor implements EntityExtractor {
731
+ private patterns;
732
+ constructor(patterns?: EntityPattern[]);
733
+ /**
734
+ * Add a new pattern.
735
+ */
736
+ addPattern(key: string, pattern: RegExp): void;
737
+ /**
738
+ * Add multiple patterns at once.
739
+ */
740
+ addPatterns(patterns: EntityPattern[]): void;
741
+ /**
742
+ * Remove a pattern by key.
743
+ */
744
+ removePattern(key: string): void;
745
+ /**
746
+ * Clear all patterns.
747
+ */
748
+ clearPatterns(): void;
749
+ /**
750
+ * Get current patterns.
751
+ */
752
+ getPatterns(): EntityPattern[];
753
+ extract(query: string): Record<string, unknown>;
754
+ }
755
+ /**
756
+ * Composite entity extractor that combines multiple extractors.
757
+ * Useful for combining pattern-based extraction with LLM-based extraction.
758
+ */
759
+ declare class CompositeEntityExtractor implements EntityExtractor {
760
+ private extractors;
761
+ constructor(extractors?: EntityExtractor[]);
762
+ addExtractor(extractor: EntityExtractor): void;
763
+ extract(query: string): Promise<Record<string, unknown>>;
764
+ }
765
+ /**
766
+ * Configuration for the RelationalStrategy.
767
+ */
768
+ interface RelationalStrategyConfig {
769
+ /** Custom entity extractor (defaults to PatternEntityExtractor) */
770
+ entityExtractor?: EntityExtractor;
771
+ /** Custom patterns for PatternEntityExtractor (ignored if entityExtractor is provided) */
772
+ patterns?: EntityPattern[];
773
+ /** Whether to include default patterns when providing custom patterns */
774
+ includeDefaultPatterns?: boolean;
775
+ }
776
+ /**
777
+ * Relational retrieval strategy.
778
+ * Finds memories related to specific entities mentioned in the query.
779
+ *
780
+ * Entity extraction is pluggable - you can:
781
+ * 1. Use the default pattern-based extractor
782
+ * 2. Provide custom regex patterns
783
+ * 3. Implement a custom EntityExtractor (e.g., using NLP or LLM)
784
+ *
785
+ * @example Default usage
786
+ * ```typescript
787
+ * const strategy = new RelationalStrategy();
788
+ * ```
789
+ *
790
+ * @example Custom patterns
791
+ * ```typescript
792
+ * const strategy = new RelationalStrategy({
793
+ * patterns: [
794
+ * { key: 'sku', pattern: /SKU[:\s]+([A-Z0-9-]+)/i },
795
+ * { key: 'barcode', pattern: /barcode[:\s]+(\d+)/i },
796
+ * ],
797
+ * includeDefaultPatterns: true, // Also include default patterns
798
+ * });
799
+ * ```
800
+ *
801
+ * @example Custom extractor
802
+ * ```typescript
803
+ * class LLMEntityExtractor implements EntityExtractor {
804
+ * async extract(query: string): Promise<Record<string, unknown>> {
805
+ * // Call LLM to extract entities
806
+ * const entities = await llm.extractEntities(query);
807
+ * return entities;
808
+ * }
809
+ * }
810
+ *
811
+ * const strategy = new RelationalStrategy({
812
+ * entityExtractor: new LLMEntityExtractor(),
813
+ * });
814
+ * ```
815
+ */
816
+ declare class RelationalStrategy implements RetrievalStrategy {
817
+ readonly type: "relational";
818
+ private entityExtractor;
819
+ constructor(config?: RelationalStrategyConfig);
820
+ /**
821
+ * Get the entity extractor (for testing or modification).
822
+ */
823
+ getEntityExtractor(): EntityExtractor;
824
+ retrieve(query: string, context: RetrievalContext, options: RetrievalOptions): Promise<ScoredMemoryEvent[]>;
825
+ /**
826
+ * Build filters from explicit context filters or by extracting entities from query.
827
+ */
828
+ private buildFilters;
829
+ }
830
+
831
+ /**
832
+ * Weights for combining different retrieval strategies.
833
+ */
834
+ interface HybridWeights {
835
+ semantic: number;
836
+ temporal: number;
837
+ relational: number;
838
+ }
839
+ /**
840
+ * Hybrid retrieval strategy.
841
+ * Combines semantic, temporal, and relational strategies with configurable weights.
842
+ */
843
+ declare class HybridStrategy implements RetrievalStrategy {
844
+ readonly type: "hybrid";
845
+ private readonly semanticStrategy;
846
+ private readonly temporalStrategy;
847
+ private readonly relationalStrategy;
848
+ private readonly weights;
849
+ constructor(weights?: Partial<HybridWeights>);
850
+ retrieve(query: string, context: RetrievalContext, options: RetrievalOptions): Promise<ScoredMemoryEvent[]>;
851
+ }
852
+
853
+ /**
854
+ * Generate a unique, sortable ID using ULID.
855
+ * ULIDs are lexicographically sortable by creation time.
856
+ */
857
+ declare function generateId(): string;
858
+ /**
859
+ * Get the timestamp from a ULID.
860
+ * @param id The ULID
861
+ * @returns The timestamp in milliseconds
862
+ */
863
+ declare function getTimestampFromId(id: string): number;
864
+
865
+ /**
866
+ * Normalize a vector to unit length.
867
+ */
868
+ declare function normalize(v: number[]): number[];
869
+ /**
870
+ * Calculate cosine similarity between two vectors.
871
+ * Returns a value between -1 and 1 (1 = identical, 0 = orthogonal, -1 = opposite).
872
+ * For normalized vectors, this is equivalent to the dot product.
873
+ */
874
+ declare function cosineSimilarity(a: number[], b: number[]): number;
875
+ /**
876
+ * Calculate Euclidean distance between two vectors.
877
+ */
878
+ declare function euclideanDistance(a: number[], b: number[]): number;
879
+
880
+ export { type AdvancedSearchOptions, Aether, type AetherConfig, CompositeEntityExtractor, DEFAULT_ENTITY_PATTERNS, type EmbeddingConfig, type EmbeddingProvider, type EntityExtractor, type EntityPattern, type EventListener, type EventRelation, HybridStrategy, type HybridWeights, InMemoryStorageAdapter, type LoggingConfig, type MemoryEvent, type MemoryEventInput, type MemoryStats, MockEmbeddingProvider, PatternEntityExtractor, type QueryOptions, RelationalStrategy, type RelationalStrategyConfig, type RerankerConfig, type RetrievalConfig, type RetrievalContext, RetrievalEngine, type RetrievalOptions, type RetrievalStrategy, type RetrievalType, type ScoredMemoryEvent, SemanticStrategy, type StorageAdapter, type StorageConfig, type TemporalQueryOptions, TemporalStrategy, type TimeRange, type Unsubscribe, type VectorSearchOptions, type VoyageModel, VoyageProvider, type VoyageProviderConfig, cosineSimilarity, euclideanDistance, generateId, getTimestampFromId, normalize };