Skip to main content
Glama
mkXultra
by mkXultra
MessageStorage.test.ts7.13 kB
import { describe, it, expect, beforeEach, afterEach } from 'vitest'; import { MessageStorage } from '../../../src/features/messaging/MessageStorage'; import { StorageError } from '../../../src/errors/AppError'; import { GetMessagesParams } from '../../../src/features/messaging/types/messaging.types'; import * as fs from 'fs/promises'; import * as path from 'path'; describe('MessageStorage', () => { let storage: MessageStorage; const testDataDir = './test-data-storage'; beforeEach(() => { storage = new MessageStorage(testDataDir); }); afterEach(async () => { // Clean up test files try { await fs.rm(testDataDir, { recursive: true, force: true }); } catch { // Ignore cleanup errors } }); describe('saveMessage', () => { it('should save message to JSONL file', async () => { const messageData = { id: '123e4567-e89b-42d3-a456-426614174000', agentName: 'test-agent', message: 'Hello world', timestamp: '2024-01-01T10:00:00.000Z', mentions: [], metadata: { priority: 'normal' } }; await storage.saveMessage('test-room', messageData); const filePath = path.join(testDataDir, 'rooms', 'test-room', 'messages.jsonl'); const content = await fs.readFile(filePath, 'utf8'); const lines = content.trim().split('\n'); expect(lines).toHaveLength(1); const savedMessage = JSON.parse(lines[0]); expect(savedMessage).toEqual(messageData); }); it('should create directory if it does not exist', async () => { const messageData = { id: '123', agentName: 'test-agent', message: 'Hello', timestamp: '2024-01-01T10:00:00.000Z', mentions: [] }; await storage.saveMessage('new-room', messageData); const dirPath = path.join(testDataDir, 'rooms', 'new-room'); const stat = await fs.stat(dirPath); expect(stat.isDirectory()).toBe(true); }); it('should append messages to existing file', async () => { const message1 = { id: '1', agentName: 'agent1', message: 'First message', timestamp: '2024-01-01T10:00:00.000Z', mentions: [] }; const message2 = { id: '2', agentName: 'agent2', message: 'Second message', timestamp: '2024-01-01T10:01:00.000Z', mentions: [] }; await storage.saveMessage('test-room', message1); await storage.saveMessage('test-room', message2); const filePath = path.join(testDataDir, 'rooms', 'test-room', 'messages.jsonl'); const content = await fs.readFile(filePath, 'utf8'); const lines = content.trim().split('\n'); expect(lines).toHaveLength(2); expect(JSON.parse(lines[0])).toEqual(message1); expect(JSON.parse(lines[1])).toEqual(message2); }); }); describe('getMessages', () => { beforeEach(async () => { // Create test messages const messages = [ { id: '1', agentName: 'alice', message: 'First message', timestamp: '2024-01-01T10:00:00.000Z', mentions: [] }, { id: '2', agentName: 'bob', message: 'Second message @alice', timestamp: '2024-01-01T10:01:00.000Z', mentions: ['alice'] }, { id: '3', agentName: 'charlie', message: 'Third message', timestamp: '2024-01-01T10:02:00.000Z', mentions: [] } ]; for (const message of messages) { await storage.saveMessage('test-room', message); } }); it('should get messages with default parameters', async () => { const params: GetMessagesParams = { roomName: 'test-room' }; const result = await storage.getMessages(params); expect(result.messages).toHaveLength(3); expect(result.hasMore).toBe(false); // Messages should be sorted by timestamp (newest first) expect(result.messages[0].id).toBe('3'); expect(result.messages[1].id).toBe('2'); expect(result.messages[2].id).toBe('1'); }); it('should apply limit to messages', async () => { const params: GetMessagesParams = { roomName: 'test-room', limit: 2 }; const result = await storage.getMessages(params); expect(result.messages).toHaveLength(2); expect(result.hasMore).toBe(true); expect(result.messages[0].id).toBe('3'); expect(result.messages[1].id).toBe('2'); }); it('should apply offset to messages', async () => { const params: GetMessagesParams = { roomName: 'test-room', limit: 2, offset: 1 }; const result = await storage.getMessages(params); expect(result.messages).toHaveLength(2); expect(result.hasMore).toBe(false); expect(result.messages[0].id).toBe('2'); expect(result.messages[1].id).toBe('1'); }); it('should filter messages by mentions', async () => { const params: GetMessagesParams = { roomName: 'test-room', agentName: 'alice', mentionsOnly: true }; const result = await storage.getMessages(params); expect(result.messages).toHaveLength(1); expect(result.messages[0].message).toBe('Second message @alice'); }); it('should return empty result for non-existent room', async () => { const params: GetMessagesParams = { roomName: 'non-existent-room' }; const result = await storage.getMessages(params); expect(result.messages).toHaveLength(0); expect(result.hasMore).toBe(false); }); }); describe('getMessageCount', () => { it('should return 0 for room with no messages', async () => { const count = await storage.getMessageCount('empty-room'); expect(count).toBe(0); }); it('should return correct count for room with messages', async () => { const messages = [ { id: '1', agentName: 'agent1', message: 'msg1', timestamp: '2024-01-01T10:00:00.000Z', mentions: [] }, { id: '2', agentName: 'agent2', message: 'msg2', timestamp: '2024-01-01T10:01:00.000Z', mentions: [] } ]; for (const message of messages) { await storage.saveMessage('test-room', message); } const count = await storage.getMessageCount('test-room'); expect(count).toBe(2); }); }); describe('error handling', () => { it('should throw StorageError for directory creation failure', async () => { // Create a file where we expect a directory const invalidPath = path.join(testDataDir, 'rooms'); await fs.mkdir(path.dirname(invalidPath), { recursive: true }); await fs.writeFile(invalidPath, 'blocking file'); const messageData = { id: '1', agentName: 'agent1', message: 'test', timestamp: '2024-01-01T10:00:00.000Z', mentions: [] }; await expect(storage.saveMessage('test-room', messageData)) .rejects.toThrow(StorageError); }); }); });

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/mkXultra/agent-communication-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server