import { config } from '../config'; interface CacheEntry { data: T; expiry: number; } class InMemoryCache { private cache: Map> = new Map(); private cleanupInterval: NodeJS.Timeout; constructor() { // Cleanup expired entries every minute this.cleanupInterval = setInterval(() => this.cleanup(), 60000); } set(key: string, value: T, ttl: number = config.cacheTTL): void { if (!config.enableCache) return; const expiry = Date.now() + (ttl * 1000); this.cache.set(key, { data: value, expiry }); } get(key: string): T | null { if (!config.enableCache) return null; const entry = this.cache.get(key); if (!entry) return null; if (Date.now() > entry.expiry) { this.cache.delete(key); return null; } return entry.data as T; } delete(key: string): void { this.cache.delete(key); } clear(): void { this.cache.clear(); } private cleanup(): void { const now = Date.now(); for (const [key, entry] of this.cache.entries()) { if (now > entry.expiry) { this.cache.delete(key); } } } destroy(): void { clearInterval(this.cleanupInterval); this.cache.clear(); } } export const cache = new InMemoryCache(); // Cache key generators export const cacheKeys = { search: (query: string, limit: number) => `search:${query}:${limit}`, image: (docId: string, type: 'thumbnail' | 'full') => `image:${docId}:${type}`, similarityMap: (docId: string, query: string) => `similarity:${docId}:${query}`, };