UNPKG

@dollhousemcp/mcp-server

Version:

DollhouseMCP - A Model Context Protocol (MCP) server that enables dynamic AI persona management from markdown files, allowing Claude and other compatible AI assistants to activate and switch between different behavioral personas.

108 lines 15.1 kB
import { EvictingQueue } from '../../utils/EvictingQueue.js'; import { LOG_LEVEL_PRIORITY } from '../types.js'; const CATEGORY_KEY = { application: 'appCapacity', security: 'securityCapacity', performance: 'perfCapacity', telemetry: 'telemetryCapacity', }; export class MemoryLogSink { queues; evictionCounts = new Map(); constructor(options) { this.queues = new Map(); for (const [category, key] of Object.entries(CATEGORY_KEY)) { this.queues.set(category, new EvictingQueue(options[key])); this.evictionCounts.set(category, 0); } } write(entry) { const queue = this.queues.get(entry.category); if (queue) { if (queue.size >= queue.capacity) { this.evictionCounts.set(entry.category, (this.evictionCounts.get(entry.category) ?? 0) + 1); } queue.push(entry); } } async flush() { // No-op — in-memory, nothing to flush. } async close() { for (const queue of this.queues.values()) { queue.clear(); } } query(options) { const category = options?.category ?? 'all'; const limit = Math.max(1, Math.min(options?.limit ?? 50, 10000)); const offset = Math.max(0, options?.offset ?? 0); // 1. Select queues const selectedQueues = []; if (category === 'all') { for (const q of this.queues.values()) { selectedQueues.push(q); } } else { const q = this.queues.get(category); if (q) selectedQueues.push(q); } // 2. Collect entries from selected queues let entries = []; for (const q of selectedQueues) { entries.push(...q.toArray()); } // 3. Apply filters conjunctively if (options?.level) { const minPriority = LOG_LEVEL_PRIORITY[options.level]; entries = entries.filter(e => LOG_LEVEL_PRIORITY[e.level] >= minPriority); } if (options?.source) { const needle = options.source.toLowerCase(); entries = entries.filter(e => e.source.toLowerCase().includes(needle)); } if (options?.message) { const needle = options.message.toLowerCase(); entries = entries.filter(e => e.message.toLowerCase().includes(needle)); } if (options?.since) { const since = options.since; entries = entries.filter(e => e.timestamp > since); } if (options?.until) { const until = options.until; entries = entries.filter(e => e.timestamp < until); } if (options?.correlationId) { const corrId = options.correlationId; entries = entries.filter(e => e.correlationId === corrId); } // 4. Count total before pagination const total = entries.length; // 5. Sort newest-first (descending timestamp) entries.sort((a, b) => (a.timestamp > b.timestamp ? -1 : a.timestamp < b.timestamp ? 1 : 0)); // 6. Paginate entries = entries.slice(offset, offset + limit); return { entries, total, hasMore: offset + limit < total, limit, offset, }; } getStats() { const stats = {}; for (const [category, queue] of this.queues) { stats[category] = { size: queue.size, capacity: queue.capacity, evictions: this.evictionCounts.get(category) ?? 0, }; } return stats; } } //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiTWVtb3J5TG9nU2luay5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3NyYy9sb2dnaW5nL3NpbmtzL01lbW9yeUxvZ1NpbmsudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLDhCQUE4QixDQUFDO0FBUTdELE9BQU8sRUFBRSxrQkFBa0IsRUFBRSxNQUFNLGFBQWEsQ0FBQztBQVNqRCxNQUFNLFlBQVksR0FBb0Q7SUFDcEUsV0FBVyxFQUFFLGFBQWE7SUFDMUIsUUFBUSxFQUFFLGtCQUFrQjtJQUM1QixXQUFXLEVBQUUsY0FBYztJQUMzQixTQUFTLEVBQUUsbUJBQW1CO0NBQy9CLENBQUM7QUFFRixNQUFNLE9BQU8sYUFBYTtJQUNQLE1BQU0sQ0FBbUQ7SUFDekQsY0FBYyxHQUE2QixJQUFJLEdBQUcsRUFBRSxDQUFDO0lBRXRFLFlBQVksT0FBNkI7UUFDdkMsSUFBSSxDQUFDLE1BQU0sR0FBRyxJQUFJLEdBQUcsRUFBK0MsQ0FBQztRQUNyRSxLQUFLLE1BQU0sQ0FBQyxRQUFRLEVBQUUsR0FBRyxDQUFDLElBQUksTUFBTSxDQUFDLE9BQU8sQ0FBQyxZQUFZLENBQUMsRUFBRSxDQUFDO1lBQzNELElBQUksQ0FBQyxNQUFNLENBQUMsR0FBRyxDQUNiLFFBQXVCLEVBQ3ZCLElBQUksYUFBYSxDQUFrQixPQUFPLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FDakQsQ0FBQztZQUNGLElBQUksQ0FBQyxjQUFjLENBQUMsR0FBRyxDQUFDLFFBQXVCLEVBQUUsQ0FBQyxDQUFDLENBQUM7UUFDdEQsQ0FBQztJQUNILENBQUM7SUFFRCxLQUFLLENBQUMsS0FBc0I7UUFDMUIsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLE1BQU0sQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLFFBQVEsQ0FBQyxDQUFDO1FBQzlDLElBQUksS0FBSyxFQUFFLENBQUM7WUFDVixJQUFJLEtBQUssQ0FBQyxJQUFJLElBQUks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LENBQUMsQ0FBQyxDQUFDO1FBRTdGLGNBQWM7UUFDZCxPQUFPLEdBQUcsT0FBTyxDQUFDLEtBQUssQ0FBQyxNQUFNLEVBQUUsTUFBTSxHQUFHLEtBQUssQ0FBQyxDQUFDO1FBRWhELE9BQU87WUFDTCxPQUFPO1lBQ1AsS0FBSztZQUNMLE9BQU8sRUFBRSxNQUFNLEdBQUcsS0FBSyxHQUFHLEtBQUs7WUFDL0IsS0FBSztZQUNMLE1BQU07U0FDUCxDQUFDO0lBQ0osQ0FBQztJQUVELFFBQVE7UUFDTixNQUFNLEtBQUssR0FBRyxFQUFnRixDQUFDO1FBQy9GLEtBQUssTUFBTSxDQUFDLFFBQVEsRUFBRSxLQUFLLENBQUMsSUFBSSxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7WUFDNUMsS0FBSyxDQUFDLFFBQVEsQ0FBQyxHQUFHO2dCQUNoQixJQUFJLEVBQUUsS0FBSyxDQUFDLElBQUk7Z0JBQ2hCLFFBQVEsRUFBRSxLQUFLLENBQUMsUUFBUTtnQkFDeEIsU0FBUyxFQUFFLElBQUksQ0FBQyxjQUFjLENBQUMsR0FBRyxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUM7YUFDbEQsQ0FBQztRQUNKLENBQUM7UUFDRCxPQUFPLEtBQUssQ0FBQztJQUNmLENBQUM7Q0FDRiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IEV2aWN0aW5nUXVldWUgfSBmcm9tICcuLi8uLi91dGlscy9FdmljdGluZ1F1ZXVlLmpzJztcbmltcG9ydCB0eXBlIHtcbiAgSUxvZ1NpbmssXG4gIExvZ0NhdGVnb3J5LFxuICBMb2dRdWVyeU9wdGlvbnMsXG4gIExvZ1F1ZXJ5UmVzdWx0LFxuICBVbmlmaWVkTG9nRW50cnksXG59IGZyb20gJy4uL3R5cGVzLmpzJztcbmltcG9ydCB7IExPR19MRVZFTF9QUklPUklUWSB9IGZyb20gJy4uL3R5cGVzLmpzJztcblxuZXhwb3J0IGludGVyZmFjZSBNZW1vcnlMb2dTaW5rT3B0aW9ucyB7XG4gIGFwcENhcGFjaXR5OiBudW1iZXI7XG4gIHNlY3VyaXR5Q2FwYWNpdHk6IG51bWJlcjtcbiAgcGVyZkNhcGFjaXR5OiBudW1iZXI7XG4gIHRlbGVtZXRyeUNhcGFjaXR5OiBudW1iZXI7XG59XG5cbmNvbnN0IENBVEVHT1JZX0tFWTogUmVjb3JkPExvZ0NhdGVnb3J5LCBrZXlvZiBNZW1vcnlMb2dTaW5rT3B0aW9ucz4gPSB7XG4gIGFwcGxpY2F0aW9uOiAnYXBwQ2FwYWNpdHknLFxuICBzZWN1cml0eTogJ3NlY3VyaXR5Q2FwYWNpdHknLFxuICBwZXJmb3JtYW5jZTogJ3BlcmZDYXBhY2l0eScsXG4gIHRlbGVtZXRyeTogJ3RlbGVtZXRyeUNhcGFjaXR5Jyxcbn07XG5cbmV4cG9ydCBjbGFzcyBNZW1vcnlMb2dTaW5rIGltcGxlbWVudHMgSUxvZ1Npbmsge1xuICBwcml2YXRlIHJlYWRvbmx5IHF1ZXVlczogTWFwPExvZ0NhdGVnb3J5LCBFdmljdGluZ1F1ZXVlPFVuaWZpZWRMb2dFbnRyeT4+O1xuICBwcml2YXRlIHJlYWRvbmx5IGV2aWN0aW9uQ291bnRzOiBNYXA8TG9nQ2F0ZWdvcnksIG51bWJlcj4gPSBuZXcgTWFwKCk7XG5cbiAgY29uc3RydWN0b3Iob3B0aW9uczogTWVtb3J5TG9nU2lua09wdGlvbnMpIHtcbiAgICB0aGlzLnF1ZXVlcyA9IG5ldyBNYXA8TG9nQ2F0ZWdvcnksIEV2aWN0aW5nUXVldWU8VW5pZmllZExvZ0VudHJ5Pj4oKTtcbiAgICBmb3IgKGNvbnN0IFtjYXRlZ29yeSwga2V5XSBvZiBPYmplY3QuZW50cmllcyhDQVRFR09SWV9LRVkpKSB7XG4gICAgICB0aGlzLnF1ZXVlcy5zZXQoXG4gICAgICAgIGNhdGVnb3J5IGFzIExvZ0NhdGVnb3J5LFxuICAgICAgICBuZXcgRXZpY3RpbmdRdWV1ZTxVbmlmaWVkTG9nRW50cnk+KG9wdGlvbnNba2V5XSksXG4gICAgICApO1xuICAgICAgdGhpcy5ldmljdGlvbkNvdW50cy5zZXQoY2F0ZWdvcnkgYXMgTG9nQ2F0ZWdvcnksIDApO1xuICAgIH1cbiAgfVxuXG4gIHdyaXRlKGVudHJ5OiBVbmlmaWVkTG9nRW50cnkpOiB2b2lkIHtcbiAgICBjb25zdCBxdWV1ZSA9IHRoaXMucXVldWVzLmdldChlbnRyeS5jYXRlZ29yeSk7XG4gICAgaWYgKHF1ZXVlKSB7XG4gICAgICBpZiAocXVldWUuc2l6ZSA+PSBxdWV1ZS5jYXBhY2l0eSkge1xuICAgICAgICB0aGlzLmV2aWN0aW9uQ291bnRzLnNldChcbiAgICAgICAgICBlbnRyeS5jYXRlZ29yeSxcbiAgICAgICAgICAodGhpcy5ldmljdGlvbkNvdW50cy5nZXQoZW50cnkuY2F0ZWdvcnkpID8/IDApICsgMSxcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICAgIHF1ZXVlLnB1c2goZW50cnkpO1xuICAgIH1cbiAgfVxuXG4gIGFzeW5jIGZsdXNoKCk6IFByb21pc2U8dm9pZD4ge1xuICAgIC8vIE5vLW9wIOKAlCBpbi1tZW1vcnksIG5vdGhpbmcgdG8gZmx1c2guXG4gIH1cblxuICBhc3luYyBjbG9zZSgpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBmb3IgKGNvbnN0IHF1ZXVlIG9mIHRoaXMucXVldWVzLnZhbHVlcygpKSB7XG4gICAgICBxdWV1ZS5jbGVhcigpO1xuICAgIH1cbiAgfVxuXG4gIHF1ZXJ5KG9wdGlvbnM/OiBMb2dRdWVyeU9wdGlvbnMpOiBMb2dRdWVyeVJlc3VsdCB7XG4gICAgY29uc3QgY2F0ZWdvcnkgPSBvcHRpb25zPy5jYXRlZ29yeSA/PyAnYWxsJztcbiAgICBjb25zdCBsaW1pdCA9IE1hdGgubWF4KDEsIE1hdGgubWluKG9wdGlvbnM/LmxpbWl0ID8/IDUwLCAxMDAwMCkpO1xuICAgIGNvbnN0IG9mZnNldCA9IE1hdGgubWF4KDAsIG9wdGlvbnM/Lm9mZnNldCA/PyAwKTtcblxuICAgIC8vIDEuIFNlbGVjdCBxdWV1ZXNcbiAgICBjb25zdCBzZWxlY3RlZFF1ZXVlczogRXZpY3RpbmdRdWV1ZTxVbmlmaWVkTG9nRW50cnk+W10gPSBbXTtcbiAgICBpZiAoY2F0ZWdvcnkgPT09ICdhbGwnKSB7XG4gICAgICBmb3IgKGNvbnN0IHEgb2YgdGhpcy5xdWV1ZXMudmFsdWVzKCkpIHtcbiAgICAgICAgc2VsZWN0ZWRRdWV1ZXMucHVzaChxKTtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgY29uc3QgcSA9IHRoaXMucXVldWVzLmdldChjYXRlZ29yeSk7XG4gICAgICBpZiAocSkgc2VsZWN0ZWRRdWV1ZXMucHVzaChxKTtcbiAgICB9XG5cbiAgICAvLyAyLiBDb2xsZWN0IGVudHJpZXMgZnJvbSBzZWxlY3RlZCBxdWV1ZXNcbiAgICBsZXQgZW50cmllczogVW5pZmllZExvZ0VudHJ5W10gPSBbXTtcbiAgICBmb3IgKGNvbnN0IHEgb2Ygc2VsZWN0ZWRRdWV1ZXMpIHtcbiAgICAgIGVudHJpZXMucHVzaCguLi5xLnRvQXJyYXkoKSk7XG4gICAgfVxuXG4gICAgLy8gMy4gQXBwbHkgZmlsdGVycyBjb25qdW5jdGl2ZWx5XG4gICAgaWYgKG9wdGlvbnM/LmxldmVsKSB7XG4gICAgICBjb25zdCBtaW5Qcmlvcml0eSA9IExPR19MRVZFTF9QUklPUklUWVtvcHRpb25zLmxldmVsXTtcbiAgICAgIGVudHJpZXMgPSBlbnRyaWVzLmZpbHRlcihlID0+IExPR19MRVZFTF9QUklPUklUWVtlLmxldmVsXSA+PSBtaW5Qcmlvcml0eSk7XG4gICAgfVxuICAgIGlmIChvcHRpb25zPy5zb3VyY2UpIHtcbiAgICAgIGNvbnN0IG5lZWRsZSA9IG9wdGlvbnMuc291cmNlLnRvTG93ZXJDYXNlKCk7XG4gICAgICBlbnRyaWVzID0gZW50cmllcy5maWx0ZXIoZSA9PiBlLnNvdXJjZS50b0xvd2VyQ2FzZSgpLmluY2x1ZGVzKG5lZWRsZSkpO1xuICAgIH1cbiAgICBpZiAob3B0aW9ucz8ubWVzc2FnZSkge1xuICAgICAgY29uc3QgbmVlZGxlID0gb3B0aW9ucy5tZXNzYWdlLnRvTG93ZXJDYXNlKCk7XG4gICAgICBlbnRyaWVzID0gZW50cmllcy5maWx0ZXIoZSA9PiBlLm1lc3NhZ2UudG9Mb3dlckNhc2UoKS5pbmNsdWRlcyhuZWVkbGUpKTtcbiAgICB9XG4gICAgaWYgKG9wdGlvbnM/LnNpbmNlKSB7XG4gICAgICBjb25zdCBzaW5jZSA9IG9wdGlvbnMuc2luY2U7XG4gICAgICBlbnRyaWVzID0gZW50cmllcy5maWx0ZXIoZSA9PiBlLnRpbWVzdGFtcCA+IHNpbmNlKTtcbiAgICB9XG4gICAgaWYgKG9wdGlvbnM/LnVudGlsKSB7XG4gICAgICBjb25zdCB1bnRpbCA9IG9wdGlvbnMudW50aWw7XG4gICAgICBlbnRyaWVzID0gZW50cmllcy5maWx0ZXIoZSA9PiBlLnRpbWVzdGFtcCA8IHVudGlsKTtcbiAgICB9XG4gICAgaWYgKG9wdGlvbnM/LmNvcnJlbGF0aW9uSWQpIHtcbiAgICAgIGNvbnN0IGNvcnJJZCA9IG9wdGlvbnMuY29ycmVsYXRpb25JZDtcbiAgICAgIGVudHJpZXMgPSBlbnRyaWVzLmZpbHRlcihlID0+IGUuY29ycmVsYXRpb25JZCA9PT0gY29ycklkKTtcbiAgICB9XG5cbiAgICAvLyA0LiBDb3VudCB0b3RhbCBiZWZvcmUgcGFnaW5hdGlvblxuICAgIGNvbnN0IHRvdGFsID0gZW50cmllcy5sZW5ndGg7XG5cbiAgICAvLyA1LiBTb3J0IG5ld2VzdC1maXJzdCAoZGVzY2VuZGluZyB0aW1lc3RhbXApXG4gICAgZW50cmllcy5zb3J0KChhLCBiKSA9PiAoYS50aW1lc3RhbXAgPiBiLnRpbWVzdGFtcCA/IC0xIDogYS50aW1lc3RhbXAgPCBiLnRpbWVzdGFtcCA/IDEgOiAwKSk7XG5cbiAgICAvLyA2LiBQYWdpbmF0ZVxuICAgIGVudHJpZXMgPSBlbnRyaWVzLnNsaWNlKG9mZnNldCwgb2Zmc2V0ICsgbGltaXQpO1xuXG4gICAgcmV0dXJuIHtcbiAgICAgIGVudHJpZXMsXG4gICAgICB0b3RhbCxcbiAgICAgIGhhc01vcmU6IG9mZnNldCArIGxpbWl0IDwgdG90YWwsXG4gICAgICBsaW1pdCxcbiAgICAgIG9mZnNldCxcbiAgICB9O1xuICB9XG5cbiAgZ2V0U3RhdHMoKTogUmVjb3JkPExvZ0NhdGVnb3J5LCB7IHNpemU6IG51bWJlcjsgY2FwYWNpdHk6IG51bWJlcjsgZXZpY3Rpb25zOiBudW1iZXIgfT4ge1xuICAgIGNvbnN0IHN0YXRzID0ge30gYXMgUmVjb3JkPExvZ0NhdGVnb3J5LCB7IHNpemU6IG51bWJlcjsgY2FwYWNpdHk6IG51bWJlcjsgZXZpY3Rpb25zOiBudW1iZXIgfT47XG4gICAgZm9yIChjb25zdCBbY2F0ZWdvcnksIHF1ZXVlXSBvZiB0aGlzLnF1ZXVlcykge1xuICAgICAgc3RhdHNbY2F0ZWdvcnldID0ge1xuICAgICAgICBzaXplOiBxdWV1ZS5zaXplLFxuICAgICAgICBjYXBhY2l0eTogcXVldWUuY2FwYWNpdHksXG4gICAgICAgIGV2aWN0aW9uczogdGhpcy5ldmljdGlvbkNvdW50cy5nZXQoY2F0ZWdvcnkpID8/IDAsXG4gICAgICB9O1xuICAgIH1cbiAgICByZXR1cm4gc3RhdHM7XG4gIH1cbn1cbiJdfQ==