UNPKG

woaru

Version:

Universal Project Setup Autopilot - Analyze and automatically configure development tools for ANY programming language

215 lines 6.88 kB
import { EventEmitter } from 'events'; /** * 🎣 WOARU Hook Manager * * Zentrale Verwaltung für alle Hook-Registrierungen und -Ausführungen. * Basiert auf Node.js EventEmitter für maximale Kompatibilität. */ export class HookManager extends EventEmitter { static instance; hookStats = new Map(); debugMode = false; constructor() { super(); this.setMaxListeners(50); // Erlaube mehr Listeners für extensible architecture } static getInstance() { if (!HookManager.instance) { HookManager.instance = new HookManager(); } return HookManager.instance; } /** * 🔗 Hook registrieren * * @param event Hook-Event Name * @param handler Handler-Funktion * @param priority Priorität (höhere Zahl = frühere Ausführung) */ registerHook(event, handler, priority = 0) { const wrappedHandler = async (data) => { try { if (this.debugMode) { console.log(`🎣 Executing hook: ${event} (priority: ${priority})`); } await handler(data); this.incrementHookStats(event); } catch (error) { console.error(`❌ Hook execution failed for ${event}:`, error); // Emit error hook if it's not already an error hook to prevent loops if (event !== 'onError') { this.triggerHook('onError', { error: error, context: `Hook execution: ${event}`, timestamp: new Date(), }); } } }; // Store priority for sorting wrappedHandler.__priority = priority; this.on(event, wrappedHandler); if (this.debugMode) { console.log(`🎣 Registered hook: ${event} (priority: ${priority})`); } } /** * 🚀 Hook auslösen * * Alle registrierten Handler für das Event werden parallel ausgeführt, * sortiert nach Priorität (höchste zuerst). * * @param event Hook-Event Name * @param data Event-Daten */ async triggerHook(event, data) { if (this.debugMode) { console.log(`🎣 Triggering hook: ${event}`); } const listeners = this.listeners(event); if (listeners.length === 0) { if (this.debugMode) { console.log(`🎣 No handlers registered for: ${event}`); } return; } // Sort by priority (höchste zuerst) const sortedListeners = listeners.sort((a, b) => { const priorityA = a.__priority || 0; const priorityB = b.__priority || 0; return priorityB - priorityA; }); // Execute all handlers in parallel const promises = sortedListeners.map(listener => listener(data)); try { await Promise.all(promises); if (this.debugMode) { console.log(`🎣 Hook completed: ${event} (${listeners.length} handlers)`); } } catch (error) { console.error(`❌ Hook execution error for ${event}:`, error); throw error; } } /** * 🗑️ Hook entfernen */ unregisterHook(event, handler) { this.removeListener(event, handler); if (this.debugMode) { console.log(`🎣 Unregistered hook: ${event}`); } } /** * 🧹 Alle Hooks eines Events entfernen */ clearHooks(event) { if (event) { this.removeAllListeners(event); if (this.debugMode) { console.log(`🎣 Cleared all hooks for: ${event}`); } } else { this.removeAllListeners(); this.hookStats.clear(); if (this.debugMode) { console.log('🎣 Cleared all hooks'); } } } /** * 📊 Hook-Statistiken */ getHookStats() { const stats = {}; for (const [event, count] of this.hookStats.entries()) { stats[event] = count; } return stats; } /** * 📋 Registrierte Hooks auflisten */ listRegisteredHooks() { const hooks = {}; const events = [ 'beforeAnalysis', 'afterAnalysis', 'beforeFileAnalysis', 'afterFileAnalysis', 'beforeToolExecution', 'afterToolExecution', 'onError', 'onConfigLoad', 'onReportGeneration', ]; for (const event of events) { hooks[event] = this.listenerCount(event); } return hooks; } /** * 🐛 Debug-Modus umschalten */ setDebugMode(enabled) { this.debugMode = enabled; console.log(`🎣 Hook debug mode: ${enabled ? 'enabled' : 'disabled'}`); } incrementHookStats(event) { const current = this.hookStats.get(event) || 0; this.hookStats.set(event, current + 1); } } /** * 🎯 Hook Utilities - Hilfs-Funktionen für häufige Hook-Patterns */ export class HookUtils { /** * Erstelle einen Hook-Handler mit automatischem Error-Handling */ static createSafeHandler(handler, context) { return async (data) => { try { await handler(data); } catch (error) { console.error(`❌ Hook handler error in ${context}:`, error); // Don't re-throw to prevent breaking the entire hook chain } }; } /** * Erstelle einen konditionalen Hook-Handler */ static createConditionalHandler(condition, handler) { return async (data) => { if (condition(data)) { await handler(data); } }; } /** * Erstelle einen Rate-Limited Hook-Handler */ static createRateLimitedHandler(handler, intervalMs) { let lastExecuted = 0; return async (data) => { const now = Date.now(); if (now - lastExecuted >= intervalMs) { lastExecuted = now; await handler(data); } }; } } // Global Hook Manager Instance Export export const hookManager = HookManager.getInstance(); // Convenience functions for common operations export const registerHook = (event, handler, priority) => hookManager.registerHook(event, handler, priority); export const triggerHook = (event, data) => hookManager.triggerHook(event, data); export const unregisterHook = (event, handler) => hookManager.unregisterHook(event, handler); export const clearHooks = (event) => hookManager.clearHooks(event); //# sourceMappingURL=HookSystem.js.map