UNPKG

@logistically/events

Version:

A production-ready event-driven architecture library for NestJS with Redis Streams, comprehensive batching, reliable consumption, and enterprise-grade features.

79 lines (78 loc) 3.23 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.EventConsumer = void 0; class EventConsumer { constructor(options) { this.handlers = options.handlers; this.onError = options.onError; if (!options.validator) { throw new Error('validator must be provided in EventConsumerOptions'); } this.validator = options.validator; this.logUnregisteredEvents = options.logUnregisteredEvents || 'debug'; } async handleMessage(rawMessage) { var _a, _b; let envelope = undefined; try { // Validate that rawMessage has the expected structure if (!rawMessage || typeof rawMessage !== 'object') { throw new Error('Invalid message: not an object'); } // Type guard to ensure proper envelope structure if (!this.isValidEnvelope(rawMessage)) { throw new Error('Invalid envelope structure: missing header or body'); } envelope = rawMessage; const { type } = envelope.header; // Validate event body using the validator const validation = this.validator.validate(type, envelope.body); if (!validation.valid) { throw new Error(`Invalid event body for type ${type}: ${validation.error}`); } const handler = this.handlers[type]; if (!handler) { // Gracefully ignore events that don't have registered handlers if (this.logUnregisteredEvents !== 'none') { console[this.logUnregisteredEvents](`[EventConsumer] No handler registered for event type: ${type}, ignoring message`); } return; } await handler(envelope.body, envelope.header, rawMessage); } catch (err) { if (this.onError) { this.onError(err, ((_b = (_a = envelope === null || envelope === void 0 ? void 0 : envelope.header) === null || _a === void 0 ? void 0 : _a.type) !== null && _b !== void 0 ? _b : 'unknown'), rawMessage); } else { throw err; } } } isValidEnvelope(message) { return (message && typeof message === 'object' && message.header && typeof message.header === 'object' && typeof message.header.id === 'string' && typeof message.header.type === 'string' && typeof message.header.origin === 'string' && typeof message.header.timestamp === 'string' && typeof message.header.hash === 'string' && typeof message.header.version === 'string' && 'body' in message); } // Method to register handlers dynamically registerHandler(eventType, handler) { this.handlers[eventType] = handler; } // Method to unregister handlers unregisterHandler(eventType) { delete this.handlers[eventType]; } // Method to get registered event types getRegisteredEventTypes() { return Object.keys(this.handlers); } } exports.EventConsumer = EventConsumer;