UNPKG

ai-debug-local-mcp

Version:

🎯 ENHANCED AI GUIDANCE v4.1.2: Dramatically improved tool descriptions help AI users choose the right tools instead of 'close enough' options. Ultra-fast keyboard automation (10x speed), universal recording, multi-ecosystem debugging support, and compreh

396 lines • 16.6 kB
/** * Bidirectional Context Sharing Manager * Enables seamless context exchange between primary agent and sub-agents * Ensures both are aware of the critical importance of context sharing */ import { EventEmitter } from 'events'; /** * Bidirectional Context Manager * Central hub for context sharing between all agents */ export class BidirectionalContextManager extends EventEmitter { contextStore = new Map(); agentAwareness = new Map(); contextSubscriptions = new Map(); // contextType -> agentIds contextDependencies = new Map(); // agentId -> contextIds they need sharingMetrics = { totalContextsShared: 0, successfulSyncs: 0, missedCriticalContext: 0, averageSyncLatency: 0 }; constructor() { super(); this.setupCriticalSharingMonitoring(); } /** * Register an agent with context sharing awareness */ registerAgent(agentId, agentType, config) { const awareness = { agentId, agentType, awarenessLevel: 'full', lastContextSync: new Date(), contextDependencies: config.contextDependencies, contextContributions: config.contextContributions, sharingImportanceScore: config.sharingImportanceScore }; this.agentAwareness.set(agentId, awareness); // Subscribe agent to context types they depend on for (const contextType of config.contextDependencies) { if (!this.contextSubscriptions.has(contextType)) { this.contextSubscriptions.set(contextType, new Set()); } this.contextSubscriptions.get(contextType).add(agentId); } this.emit('agent_registered', { agentId, awareness }); } /** * Share context from any agent to relevant agents */ async shareContext(context) { const contextId = `ctx-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`; const contextEntry = { id: contextId, timestamp: new Date(), ...context }; this.contextStore.set(contextId, contextEntry); this.sharingMetrics.totalContextsShared++; // Determine target agents based on sharing configuration and subscriptions const targetAgents = this.determineTargetAgents(contextEntry); // Create synchronization event const syncEvent = { eventType: 'context_added', targetAgents, contextId, urgency: this.calculateUrgency(contextEntry), syncMetadata: { requiredFor: contextEntry.content.title, deadline: contextEntry.priority === 'critical' ? new Date(Date.now() + 60000) : undefined } }; // Perform bidirectional synchronization await this.synchronizeContext(syncEvent); // Emit context sharing event this.emit('context_shared', { contextEntry, targetAgents, syncEvent }); return contextId; } /** * Request specific context (pull model) */ async requestContext(requestingAgentId, contextType, criteria) { const relevantContexts = Array.from(this.contextStore.values()) .filter(ctx => { // Match type if (ctx.type !== contextType) return false; // Match priority if specified if (criteria.priority && ctx.priority !== criteria.priority) return false; // Check age if specified if (criteria.maxAge) { const age = Date.now() - ctx.timestamp.getTime(); if (age > criteria.maxAge) return false; } return true; }) .sort((a, b) => b.timestamp.getTime() - a.timestamp.getTime()); // Newest first // Record context request this.emit('context_requested', { requestingAgentId, contextType, criteria, foundCount: relevantContexts.length }); // Update agent's last sync time const awareness = this.agentAwareness.get(requestingAgentId); if (awareness) { awareness.lastContextSync = new Date(); this.agentAwareness.set(requestingAgentId, awareness); } // Track dependency if (!this.contextDependencies.has(requestingAgentId)) { this.contextDependencies.set(requestingAgentId, []); } const dependencies = this.contextDependencies.get(requestingAgentId); const contextIds = relevantContexts.map(ctx => ctx.id); this.contextDependencies.set(requestingAgentId, [...new Set([...dependencies, ...contextIds])]); return relevantContexts; } /** * Update existing context (collaborative refinement) */ async updateContext(contextId, updatingAgentId, updates) { const context = this.contextStore.get(contextId); if (!context) return false; // Merge updates const updatedContext = { ...context, content: { ...context.content, ...updates.content }, contextual: { ...context.contextual, ...updates.contextual } }; // Add updating agent's insights if (updates.additionalInsights) { if (!updatedContext.content.recommendations) { updatedContext.content.recommendations = []; } updatedContext.content.recommendations.push(...updates.additionalInsights.map(insight => `[${updatingAgentId}]: ${insight}`)); } this.contextStore.set(contextId, updatedContext); // Notify other agents of the update const targetAgents = this.determineTargetAgents(updatedContext) .filter(agentId => agentId !== updatingAgentId); // Don't notify the updating agent const syncEvent = { eventType: 'context_updated', targetAgents, contextId, urgency: 'normal', syncMetadata: { requiredFor: `Context update by ${updatingAgentId}` } }; await this.synchronizeContext(syncEvent); this.emit('context_updated', { contextId, updatingAgentId, updates, targetAgents }); return true; } /** * Get agent's context awareness status */ getAgentAwareness(agentId) { return this.agentAwareness.get(agentId) || null; } /** * Get comprehensive context sharing status */ getContextSharingStatus() { const recentActivity = Array.from(this.contextStore.values()) .sort((a, b) => b.timestamp.getTime() - a.timestamp.getTime()) .slice(0, 10); const criticalGaps = this.identifyCriticalContextGaps(); return { totalContexts: this.contextStore.size, activeAgents: this.agentAwareness.size, sharingMetrics: { ...this.sharingMetrics }, recentActivity, criticalGaps }; } /** * Emphasize context sharing importance to agents */ emphasizeContextSharingImportance(agentId, scenario) { const awareness = this.agentAwareness.get(agentId); if (!awareness) { return { importance: 'critical', reasoning: 'Agent not registered - context sharing is essential for coordination', recommendations: ['Register with context manager immediately', 'Share all discoveries and decisions'] }; } const importance = this.calculateContextImportance(awareness, scenario); const reasoning = this.generateImportanceReasoning(awareness, scenario, importance); const recommendations = this.generateContextSharingRecommendations(awareness, scenario); return { importance, reasoning, recommendations }; } /** * Determine target agents for context sharing */ determineTargetAgents(context) { const targets = new Set(); // Add agents subscribed to this context type const subscribers = this.contextSubscriptions.get(context.type) || new Set(); subscribers.forEach(agentId => targets.add(agentId)); // Add specific sharing targets based on configuration if (context.sharing.shareWithPrimary) { const primaryAgents = Array.from(this.agentAwareness.values()) .filter(a => a.agentType === 'primary') .map(a => a.agentId); primaryAgents.forEach(agentId => targets.add(agentId)); } if (context.sharing.shareWithSubAgents) { const subAgents = Array.from(this.agentAwareness.values()) .filter(a => a.agentType === 'sub') .map(a => a.agentId); subAgents.forEach(agentId => targets.add(agentId)); } if (context.sharing.shareWithBackground) { const backgroundAgents = Array.from(this.agentAwareness.values()) .filter(a => a.agentType === 'background') .map(a => a.agentId); backgroundAgents.forEach(agentId => targets.add(agentId)); } // Don't include the source agent targets.delete(context.sourceId); return Array.from(targets); } /** * Calculate urgency for context synchronization */ calculateUrgency(context) { if (context.priority === 'critical') return 'immediate'; if (context.priority === 'high') return 'high'; if (context.sharing.criticalForDecisionMaking) return 'high'; if (context.type === 'error') return 'high'; return 'normal'; } /** * Perform bidirectional context synchronization */ async synchronizeContext(syncEvent) { const startTime = Date.now(); for (const targetAgentId of syncEvent.targetAgents) { try { await this.syncContextToAgent(targetAgentId, syncEvent); this.sharingMetrics.successfulSyncs++; } catch (error) { this.emit('sync_error', { targetAgentId, syncEvent, error }); if (syncEvent.urgency === 'immediate') { this.sharingMetrics.missedCriticalContext++; } } } const syncLatency = Date.now() - startTime; this.sharingMetrics.averageSyncLatency = (this.sharingMetrics.averageSyncLatency + syncLatency) / 2; this.emit('context_synchronized', { syncEvent, syncLatency }); } /** * Sync context to a specific agent */ async syncContextToAgent(agentId, syncEvent) { const awareness = this.agentAwareness.get(agentId); if (!awareness) { throw new Error(`Agent ${agentId} not registered for context sharing`); } const context = this.contextStore.get(syncEvent.contextId); if (!context) { throw new Error(`Context ${syncEvent.contextId} not found`); } // Update agent's last sync time awareness.lastContextSync = new Date(); this.agentAwareness.set(agentId, awareness); // Emit agent-specific sync event this.emit('agent_context_sync', { agentId, context, syncEvent, awareness }); } /** * Setup monitoring for critical context sharing */ setupCriticalSharingMonitoring() { // Monitor for agents that haven't synced recently setInterval(() => { const staleThreshold = 300000; // 5 minutes const now = Date.now(); for (const [agentId, awareness] of this.agentAwareness.entries()) { const timeSinceSync = now - awareness.lastContextSync.getTime(); if (timeSinceSync > staleThreshold && awareness.sharingImportanceScore > 0.7) { this.emit('agent_context_stale', { agentId, awareness, timeSinceSync }); } } }, 60000); // Check every minute // Monitor for critical context that wasn't acknowledged this.on('context_shared', ({ contextEntry, targetAgents }) => { if (contextEntry.sharing.requiresAcknowledgment) { setTimeout(() => { this.emit('acknowledgment_timeout', { contextId: contextEntry.id, targetAgents, context: contextEntry }); }, 30000); // 30 second timeout for acknowledgment } }); } /** * Identify critical context gaps */ identifyCriticalContextGaps() { const gaps = []; // Check for agents with high sharing importance but low recent activity for (const [agentId, awareness] of this.agentAwareness.entries()) { if (awareness.sharingImportanceScore > 0.8) { const timeSinceSync = Date.now() - awareness.lastContextSync.getTime(); if (timeSinceSync > 600000) { // 10 minutes gaps.push(`Agent ${agentId} has high sharing importance but hasn't synced in ${Math.round(timeSinceSync / 60000)} minutes`); } } } // Check for missing critical context types const criticalTypes = ['error', 'decision', 'discovery']; const recentContextTypes = new Set(Array.from(this.contextStore.values()) .filter(ctx => Date.now() - ctx.timestamp.getTime() < 300000) // Last 5 minutes .map(ctx => ctx.type)); for (const criticalType of criticalTypes) { if (!recentContextTypes.has(criticalType)) { gaps.push(`No recent ${criticalType} context shared - may indicate communication gap`); } } return gaps; } /** * Calculate context sharing importance for an agent */ calculateContextImportance(awareness, scenario) { if (awareness.sharingImportanceScore > 0.8) return 'critical'; if (awareness.sharingImportanceScore > 0.6) return 'high'; return 'medium'; } /** * Generate reasoning for context sharing importance */ generateImportanceReasoning(awareness, scenario, importance) { const baseReasoning = `Context sharing is ${importance} for ${awareness.agentType} agent ${awareness.agentId}`; if (importance === 'critical') { return `${baseReasoning} because coordinated decision-making depends on shared understanding. Without bidirectional context, agents make suboptimal decisions that impact the entire system.`; } else if (importance === 'high') { return `${baseReasoning} because effective collaboration requires shared situational awareness. Context gaps lead to duplicated work and missed optimizations.`; } else { return `${baseReasoning} for maintaining coordination and avoiding conflicts between agent actions.`; } } /** * Generate context sharing recommendations */ generateContextSharingRecommendations(awareness, scenario) { const recommendations = []; if (awareness.agentType === 'primary') { recommendations.push('Share all major decisions and discoveries with sub-agents immediately'); recommendations.push('Request progress updates from sub-agents every 2-3 minutes'); recommendations.push('Maintain awareness of background agent findings'); } else if (awareness.agentType === 'sub') { recommendations.push('Continuously update primary agent on progress and findings'); recommendations.push('Share insights that could affect other sub-agents'); recommendations.push('Request context when encountering unfamiliar situations'); } else { recommendations.push('Proactively share critical findings and alerts'); recommendations.push('Provide context about system state changes'); } recommendations.push('Use high-priority sharing for time-sensitive information'); recommendations.push('Update shared context collaboratively when new insights emerge'); return recommendations; } } //# sourceMappingURL=bidirectional-context-manager.js.map