UNPKG

stellar-cyber-mcp-agents

Version:

Model Context Protocol (MCP) server for Stellar Cyber security operations with specialized multi-agent analysis capabilities

929 lines 35.8 kB
import { BaseAgent } from '../core/base-agent.js'; import { AgentHealth } from '../types/agent.js'; export class NetworkAnalysisAgent extends BaseAgent { config; activeAnalyses = new Map(); analysisCache = new Map(); threatPatterns = new Map(); accessToken = null; tokenExpiresAt = 0; refreshPromise = null; constructor(metadata, registry, channel, logger, metrics, config) { super(metadata, registry, channel, logger, metrics); this.config = { analysisTimeout: 300000, // 5 minutes maxConcurrentAnalysis: 10, enableDeepPacketAnalysis: true, ...config }; } async onInitialize() { this.logger.info('Initializing Network Analysis Agent'); // Initialize authentication await this.refreshToken(); // Load threat patterns await this.loadThreatPatterns(); this.logger.info('Network Analysis Agent initialized successfully'); } async onStart() { this.logger.info('Starting Network Analysis Agent'); // Start periodic pattern updates this.startPatternUpdates(); this.logger.info('Network Analysis Agent started successfully'); } async onStop() { this.logger.info('Stopping Network Analysis Agent'); // Cancel any active analyses await this.cancelActiveAnalyses(); this.logger.info('Network Analysis Agent stopped successfully'); } async onDestroy() { this.logger.info('Destroying Network Analysis Agent'); // Clear all state this.activeAnalyses.clear(); this.analysisCache.clear(); this.threatPatterns.clear(); this.logger.info('Network Analysis Agent destroyed successfully'); } async onHealthCheck() { try { // Check API connectivity const response = await this.makeRequest('GET', '/connect/api/v1/health'); // Check active analyses const activeCount = this.activeAnalyses.size; if (!response.ok) { return AgentHealth.DEGRADED; } if (activeCount > this.config.maxConcurrentAnalysis * 0.9) { return AgentHealth.DEGRADED; } return AgentHealth.HEALTHY; } catch (error) { this.logger.error('Health check failed', { error }); return AgentHealth.UNHEALTHY; } } async handleRequest(request, context) { const { capability, payload } = request; this.logger.debug('Handling Network Analysis Agent request', { capability, requestId: request.id, sourceAgent: request.sourceAgentId }); switch (capability) { case 'analyze_network_activity': return await this.analyzeNetworkActivity(payload.caseId, payload.timeRange, payload.options); case 'detect_lateral_movement': return await this.detectLateralMovement(payload.caseId, payload.timeRange); case 'analyze_data_exfiltration': return await this.analyzeDataExfiltration(payload.caseId, payload.timeRange); case 'detect_c2_communication': return await this.detectC2Communication(payload.caseId, payload.indicators); case 'analyze_traffic_patterns': return await this.analyzeTrafficPatterns(payload.connections); case 'get_network_topology': return await this.getNetworkTopology(payload.caseId, payload.timeRange); case 'analyze_protocol_anomalies': return await this.analyzeProtocolAnomalies(payload.caseId, payload.protocols); case 'hunt_network_threats': return await this.huntNetworkThreats(payload.query, payload.timeRange); case 'generate_network_timeline': return await this.generateNetworkTimeline(payload.caseId, payload.timeRange); case 'analyze_endpoint_behavior': return await this.analyzeEndpointBehavior(payload.endpoint, payload.timeRange); default: throw new Error(`Unknown capability: ${capability}`); } } async analyzeNetworkActivity(caseId, timeRange, options = {}) { const analysisId = crypto.randomUUID(); this.logger.info('Starting network activity analysis', { analysisId, caseId, timeRange }); // Check cache const cacheKey = `${caseId}-${JSON.stringify(timeRange)}`; const cached = this.analysisCache.get(cacheKey); if (cached) { return cached; } // Check if analysis is already running const existingAnalysis = this.activeAnalyses.get(cacheKey); if (existingAnalysis) { return await existingAnalysis; } // Start new analysis const analysisPromise = this.performNetworkAnalysis(analysisId, caseId, timeRange, options); this.activeAnalyses.set(cacheKey, analysisPromise); try { const result = await analysisPromise; // Cache result this.analysisCache.set(cacheKey, result); // Cleanup this.activeAnalyses.delete(cacheKey); return result; } catch (error) { this.activeAnalyses.delete(cacheKey); throw error; } } async performNetworkAnalysis(analysisId, caseId, timeRange, options) { try { // Fetch network data const [connections, flows, alerts] = await Promise.all([ this.fetchNetworkConnections(caseId, timeRange), this.fetchNetworkFlows(caseId, timeRange), this.fetchNetworkAlerts(caseId, timeRange) ]); // Analyze connections const connectionAnalysis = await this.analyzeConnections(connections); // Detect threats const threats = await this.detectThreats(connections, flows, alerts); // Generate findings const findings = await this.generateNetworkFindings(connectionAnalysis, threats, flows, alerts); // Build visualizations const visualizations = await this.buildNetworkVisualizations(connections, threats, findings); // Generate recommendations const recommendations = this.generateNetworkRecommendations(findings, threats); // Calculate summary const summary = this.calculateNetworkSummary(connections, findings, threats); const analysis = { id: analysisId, caseId, timestamp: new Date().toISOString(), summary, findings, connections: connections.slice(0, 100), // Limit for response size threats, recommendations, visualizations }; this.logger.info('Network activity analysis completed', { analysisId, caseId, findingsCount: findings.length, threatsCount: threats.length }); return analysis; } catch (error) { this.logger.error('Network activity analysis failed', { analysisId, caseId, error }); throw error; } } async detectLateralMovement(caseId, timeRange) { this.logger.info('Detecting lateral movement', { caseId, timeRange }); try { const connections = await this.fetchNetworkConnections(caseId, timeRange); // Analyze internal-to-internal connections const internalConnections = connections.filter(conn => this.isInternalIP(conn.source.ip) && this.isInternalIP(conn.destination.ip)); // Look for suspicious patterns const suspiciousPatterns = this.detectSuspiciousLateralPatterns(internalConnections); // Identify pivot points const pivotPoints = this.identifyPivotPoints(internalConnections); // Build movement chains const movementChains = this.buildMovementChains(internalConnections, pivotPoints); const result = { detected: movementChains.length > 0, confidence: this.calculateLateralMovementConfidence(movementChains, suspiciousPatterns), movementChains, pivotPoints, suspiciousPatterns, recommendations: this.generateLateralMovementRecommendations(movementChains) }; this.logger.info('Lateral movement detection completed', { caseId, detected: result.detected, chainsFound: movementChains.length }); return result; } catch (error) { this.logger.error('Lateral movement detection failed', { caseId, error }); throw error; } } async analyzeDataExfiltration(caseId, timeRange) { this.logger.info('Analyzing data exfiltration', { caseId, timeRange }); try { const connections = await this.fetchNetworkConnections(caseId, timeRange); // Find large outbound transfers const largeTransfers = connections.filter(conn => conn.bytesTransferred > 100 * 1024 * 1024 && // 100MB !this.isInternalIP(conn.destination.ip)); // Analyze transfer patterns const transferPatterns = this.analyzeTransferPatterns(largeTransfers); // Check for suspicious destinations const suspiciousDestinations = await this.checkDestinationReputation(largeTransfers.map(c => c.destination)); // Detect encoding/encryption const encodingAnalysis = this.detectDataEncoding(largeTransfers); const result = { suspiciousTransfers: largeTransfers.length, totalDataTransferred: largeTransfers.reduce((sum, c) => sum + c.bytesTransferred, 0), transferPatterns, suspiciousDestinations, encodingAnalysis, riskLevel: this.calculateExfiltrationRisk(largeTransfers, suspiciousDestinations), recommendations: this.generateExfiltrationRecommendations(largeTransfers) }; this.logger.info('Data exfiltration analysis completed', { caseId, suspiciousTransfers: result.suspiciousTransfers, riskLevel: result.riskLevel }); return result; } catch (error) { this.logger.error('Data exfiltration analysis failed', { caseId, error }); throw error; } } async detectC2Communication(caseId, indicators) { this.logger.info('Detecting C2 communication', { caseId, indicatorCount: indicators.length }); try { const connections = await this.fetchNetworkConnections(caseId, {}); // Find connections matching indicators const c2Connections = connections.filter(conn => indicators.includes(conn.destination.ip) || indicators.includes(conn.destination.hostname || '')); // Analyze communication patterns const patterns = this.analyzeC2Patterns(c2Connections); // Detect beaconing behavior const beaconing = this.detectBeaconing(c2Connections); // Check for common C2 protocols const protocolAnalysis = this.analyzeC2Protocols(c2Connections); const result = { detected: c2Connections.length > 0, confidence: this.calculateC2Confidence(c2Connections, patterns, beaconing), connections: c2Connections, patterns, beaconing, protocolAnalysis, recommendations: this.generateC2Recommendations(c2Connections) }; this.logger.info('C2 communication detection completed', { caseId, detected: result.detected, connectionsFound: c2Connections.length }); return result; } catch (error) { this.logger.error('C2 communication detection failed', { caseId, error }); throw error; } } async analyzeTrafficPatterns(connections) { this.logger.info('Analyzing traffic patterns', { connectionCount: connections.length }); const patterns = []; // Apply threat patterns for (const [patternId, pattern] of this.threatPatterns) { const matches = this.matchPattern(connections, pattern); if (matches.length > 0) { patterns.push({ ...pattern, matchCount: matches.length }); } } // Analyze temporal patterns const temporalPatterns = this.analyzeTemporalPatterns(connections); // Analyze volumetric patterns const volumetricPatterns = this.analyzeVolumetricPatterns(connections); // Analyze behavioral patterns const behavioralPatterns = this.analyzeBehavioralPatterns(connections); return { patterns, temporalPatterns, volumetricPatterns, behavioralPatterns, anomalies: this.detectPatternAnomalies(connections), summary: this.summarizePatterns(patterns) }; } async getNetworkTopology(caseId, timeRange) { this.logger.info('Building network topology', { caseId, timeRange }); try { const connections = await this.fetchNetworkConnections(caseId, timeRange); // Build node map const nodes = this.buildNetworkNodes(connections); // Build edges const edges = this.buildNetworkEdges(connections); // Calculate node metrics const nodeMetrics = this.calculateNodeMetrics(nodes, edges); // Identify critical nodes const criticalNodes = this.identifyCriticalNodes(nodeMetrics); // Build topology visualization const topology = { nodes: Array.from(nodes.values()), edges, metrics: nodeMetrics, criticalNodes, clusters: this.identifyNetworkClusters(nodes, edges), summary: { totalNodes: nodes.size, totalEdges: edges.length, avgDegree: this.calculateAverageDegree(nodes, edges), density: this.calculateNetworkDensity(nodes.size, edges.length) } }; this.logger.info('Network topology built', { caseId, nodeCount: topology.summary.totalNodes, edgeCount: topology.summary.totalEdges }); return topology; } catch (error) { this.logger.error('Failed to build network topology', { caseId, error }); throw error; } } async analyzeProtocolAnomalies(caseId, protocols) { this.logger.info('Analyzing protocol anomalies', { caseId, protocols }); try { const connections = await this.fetchNetworkConnections(caseId, {}); const analyses = []; for (const protocol of protocols) { const protocolConnections = connections.filter(c => c.protocol === protocol); const analysis = { protocol, totalConnections: protocolConnections.length, suspiciousConnections: 0, anomalies: [], risks: [] }; // Detect anomalies based on protocol switch (protocol.toLowerCase()) { case 'http': case 'https': analysis.anomalies.push(...this.detectHTTPAnomalies(protocolConnections)); break; case 'dns': analysis.anomalies.push(...this.detectDNSAnomalies(protocolConnections)); break; case 'ssh': analysis.anomalies.push(...this.detectSSHAnomalies(protocolConnections)); break; case 'rdp': analysis.anomalies.push(...this.detectRDPAnomalies(protocolConnections)); break; } analysis.suspiciousConnections = analysis.anomalies.reduce((sum, a) => sum + a.connections.length, 0); analyses.push(analysis); } return { analyses, summary: this.summarizeProtocolAnomalies(analyses), recommendations: this.generateProtocolRecommendations(analyses) }; } catch (error) { this.logger.error('Protocol anomaly analysis failed', { caseId, error }); throw error; } } async huntNetworkThreats(query, timeRange) { this.logger.info('Hunting network threats', { query, timeRange }); try { // Search for threat indicators const connections = await this.searchConnections(query, timeRange); // Apply threat hunting rules const huntingResults = await this.applyHuntingRules(connections); // Correlate with threat intelligence const threatIntel = await this.correlateThreatIntel(connections); // Generate hunt findings const findings = this.generateHuntFindings(huntingResults, threatIntel); return { threatsFound: findings.length, findings, indicators: this.extractHuntIndicators(findings), recommendations: this.generateHuntRecommendations(findings), nextSteps: this.suggestNextHuntSteps(findings) }; } catch (error) { this.logger.error('Network threat hunting failed', { error }); throw error; } } async generateNetworkTimeline(caseId, timeRange) { this.logger.info('Generating network timeline', { caseId, timeRange }); try { const connections = await this.fetchNetworkConnections(caseId, timeRange); // Build timeline events const events = connections.map(conn => ({ timestamp: conn.timestamp, type: 'connection', description: `${conn.source.ip}:${conn.source.port} → ${conn.destination.ip}:${conn.destination.port}`, protocol: conn.protocol, severity: this.getConnectionSeverity(conn), details: conn })); // Add network alerts const alerts = await this.fetchNetworkAlerts(caseId, timeRange); alerts.forEach(alert => { events.push({ timestamp: alert.timestamp, type: 'alert', description: alert.description, protocol: alert.protocol || 'unknown', severity: alert.severity, details: alert }); }); // Sort chronologically events.sort((a, b) => new Date(a.timestamp).getTime() - new Date(b.timestamp).getTime()); return { events, summary: { totalEvents: events.length, timespan: this.calculateTimespan(events), severityBreakdown: this.calculateSeverityBreakdown(events) } }; } catch (error) { this.logger.error('Failed to generate network timeline', { caseId, error }); throw error; } } async analyzeEndpointBehavior(endpoint, timeRange) { this.logger.info('Analyzing endpoint behavior', { endpoint, timeRange }); try { // Get all connections for endpoint const connections = await this.fetchEndpointConnections(endpoint, timeRange); // Analyze communication patterns const communicationPatterns = this.analyzeEndpointCommunication(connections); // Detect anomalous behavior const anomalies = this.detectEndpointAnomalies(connections); // Profile endpoint const profile = this.profileEndpoint(connections); // Risk assessment const riskAssessment = this.assessEndpointRisk(profile, anomalies); return { endpoint, profile, communicationPatterns, anomalies, riskAssessment, recommendations: this.generateEndpointRecommendations(riskAssessment) }; } catch (error) { this.logger.error('Endpoint behavior analysis failed', { endpoint, error }); throw error; } } // Helper methods async refreshToken() { if (this.refreshPromise) { return this.refreshPromise; } this.refreshPromise = this.performTokenRefresh(); try { await this.refreshPromise; } finally { this.refreshPromise = null; } } async performTokenRefresh() { const response = await fetch(`${this.config.apiUrl}/connect/api/v1/access_token`, { method: 'POST', headers: { 'Authorization': `Bearer ${this.config.apiToken}`, 'Content-Type': 'application/json' } }); if (!response.ok) { throw new Error(`Token refresh failed: ${response.status}`); } const data = await response.json(); this.accessToken = data.access_token; this.tokenExpiresAt = Date.now() + (data.exp * 1000); } async getAccessToken() { if (this.accessToken && Date.now() < this.tokenExpiresAt - 30000) { return this.accessToken; } await this.refreshToken(); return this.accessToken; } async makeRequest(method, endpoint, body) { const token = await this.getAccessToken(); const options = { method, headers: { 'Authorization': `Bearer ${token}`, 'Content-Type': 'application/json', } }; if (body) { options.body = JSON.stringify(body); } const response = await fetch(`${this.config.apiUrl}${endpoint}`, options); return response; } async loadThreatPatterns() { // Load default threat patterns const defaultPatterns = [ { id: 'port-scan', name: 'Port Scanning', description: 'Multiple connections to different ports from same source', indicators: ['multiple_ports', 'short_duration', 'failed_connections'], matchCount: 0, severity: 'HIGH', recommendation: 'Block source IP and investigate for compromise' }, { id: 'data-exfil', name: 'Data Exfiltration', description: 'Large outbound data transfers to external IPs', indicators: ['large_transfer', 'external_destination', 'off_hours'], matchCount: 0, severity: 'CRITICAL', recommendation: 'Immediately investigate and potentially block transfers' }, { id: 'c2-beacon', name: 'C2 Beaconing', description: 'Regular periodic connections to external hosts', indicators: ['periodic', 'consistent_size', 'external_destination'], matchCount: 0, severity: 'CRITICAL', recommendation: 'Isolate infected host and block C2 infrastructure' } ]; defaultPatterns.forEach(pattern => { this.threatPatterns.set(pattern.id, pattern); }); } async fetchNetworkConnections(caseId, timeRange) { // Simulate fetching network connections return []; } async fetchNetworkFlows(caseId, timeRange) { return []; } async fetchNetworkAlerts(caseId, timeRange) { return []; } async analyzeConnections(connections) { return { totalAnalyzed: connections.length, suspicious: connections.filter(c => c.classification === 'suspicious').length, malicious: connections.filter(c => c.classification === 'malicious').length }; } async detectThreats(connections, flows, alerts) { return []; } async generateNetworkFindings(connectionAnalysis, threats, flows, alerts) { return []; } async buildNetworkVisualizations(connections, threats, findings) { return []; } generateNetworkRecommendations(findings, threats) { const recommendations = []; if (findings.some(f => f.type === 'data_exfiltration')) { recommendations.push('Implement DLP controls on network perimeter'); recommendations.push('Review and restrict outbound traffic policies'); } if (findings.some(f => f.type === 'lateral_movement')) { recommendations.push('Implement network segmentation'); recommendations.push('Deploy EDR on all endpoints'); } if (threats.length > 0) { recommendations.push('Update IDS/IPS signatures'); recommendations.push('Conduct threat hunting exercises'); } return recommendations; } calculateNetworkSummary(connections, findings, threats) { const uniqueIPs = new Set([ ...connections.map(c => c.source.ip), ...connections.map(c => c.destination.ip) ]); const protocols = connections.reduce((acc, conn) => { acc[conn.protocol] = (acc[conn.protocol] || 0) + 1; return acc; }, {}); const dataTransferred = connections.reduce((acc, conn) => { if (this.isInternalIP(conn.source.ip) && !this.isInternalIP(conn.destination.ip)) { acc.outbound += conn.bytesTransferred; } else if (!this.isInternalIP(conn.source.ip) && this.isInternalIP(conn.destination.ip)) { acc.inbound += conn.bytesTransferred; } return acc; }, { inbound: 0, outbound: 0 }); const riskLevel = this.calculateOverallRiskLevel(findings, threats); return { totalConnections: connections.length, uniqueIPs: uniqueIPs.size, suspiciousConnections: connections.filter(c => c.classification === 'suspicious').length, dataTransferred, protocols, riskLevel }; } calculateOverallRiskLevel(findings, threats) { if (findings.some(f => f.severity === 'CRITICAL') || threats.some(t => t.severity === 'CRITICAL')) { return 'CRITICAL'; } if (findings.some(f => f.severity === 'HIGH') || threats.some(t => t.severity === 'HIGH')) { return 'HIGH'; } if (findings.some(f => f.severity === 'MEDIUM') || threats.some(t => t.severity === 'MEDIUM')) { return 'MEDIUM'; } return 'LOW'; } isInternalIP(ip) { return ip.startsWith('10.') || ip.startsWith('172.') || ip.startsWith('192.168.'); } detectSuspiciousLateralPatterns(connections) { return []; } identifyPivotPoints(connections) { return []; } buildMovementChains(connections, pivotPoints) { return []; } calculateLateralMovementConfidence(chains, patterns) { return 0.8; } generateLateralMovementRecommendations(chains) { return ['Implement network segmentation', 'Deploy EDR solutions']; } analyzeTransferPatterns(transfers) { return {}; } async checkDestinationReputation(endpoints) { return []; } detectDataEncoding(transfers) { return {}; } calculateExfiltrationRisk(transfers, suspicious) { return 'HIGH'; } generateExfiltrationRecommendations(transfers) { return ['Implement DLP controls', 'Monitor large outbound transfers']; } analyzeC2Patterns(connections) { return {}; } detectBeaconing(connections) { return {}; } analyzeC2Protocols(connections) { return {}; } calculateC2Confidence(connections, patterns, beaconing) { return 0.85; } generateC2Recommendations(connections) { return ['Block C2 infrastructure', 'Isolate infected systems']; } matchPattern(connections, pattern) { return []; } analyzeTemporalPatterns(connections) { return {}; } analyzeVolumetricPatterns(connections) { return {}; } analyzeBehavioralPatterns(connections) { return {}; } detectPatternAnomalies(connections) { return []; } summarizePatterns(patterns) { return {}; } buildNetworkNodes(connections) { return new Map(); } buildNetworkEdges(connections) { return []; } calculateNodeMetrics(nodes, edges) { return {}; } identifyCriticalNodes(metrics) { return []; } identifyNetworkClusters(nodes, edges) { return []; } calculateAverageDegree(nodes, edges) { return 0; } calculateNetworkDensity(nodeCount, edgeCount) { return 0; } detectHTTPAnomalies(connections) { return []; } detectDNSAnomalies(connections) { return []; } detectSSHAnomalies(connections) { return []; } detectRDPAnomalies(connections) { return []; } summarizeProtocolAnomalies(analyses) { return {}; } generateProtocolRecommendations(analyses) { return []; } async searchConnections(query, timeRange) { return []; } async applyHuntingRules(connections) { return {}; } async correlateThreatIntel(connections) { return {}; } generateHuntFindings(huntingResults, threatIntel) { return []; } extractHuntIndicators(findings) { return []; } generateHuntRecommendations(findings) { return []; } suggestNextHuntSteps(findings) { return []; } getConnectionSeverity(connection) { if (connection.classification === 'malicious') return 'CRITICAL'; if (connection.classification === 'suspicious') return 'HIGH'; return 'LOW'; } calculateTimespan(events) { return '24 hours'; } calculateSeverityBreakdown(events) { return {}; } async fetchEndpointConnections(endpoint, timeRange) { return []; } analyzeEndpointCommunication(connections) { return {}; } detectEndpointAnomalies(connections) { return []; } profileEndpoint(connections) { return {}; } assessEndpointRisk(profile, anomalies) { return {}; } generateEndpointRecommendations(riskAssessment) { return []; } startPatternUpdates() { // Skip background timers in MCP mode to prevent EPIPE errors if (process.env.MCP_MODE === 'true') return; setInterval(() => { this.updateThreatPatterns().catch(error => { this.logger.error('Failed to update threat patterns', { error }); }); }, 3600000); // Update every hour } async updateThreatPatterns() { // Update threat patterns from threat intelligence sources } async cancelActiveAnalyses() { // Cancel any running analyses this.activeAnalyses.clear(); } } export function createNetworkAnalysisAgentMetadata() { const capabilities = [ { name: 'analyze_network_activity', description: 'Comprehensive network activity analysis', inputSchema: { type: 'object', properties: { caseId: { type: 'string' }, timeRange: { type: 'object' }, options: { type: 'object' } }, required: ['caseId'] }, outputSchema: { type: 'object', properties: { summary: { type: 'object' }, findings: { type: 'array' }, threats: { type: 'array' }, recommendations: { type: 'array' } } } }, { name: 'detect_lateral_movement', description: 'Detect lateral movement in network', inputSchema: { type: 'object', properties: { caseId: { type: 'string' }, timeRange: { type: 'object' } }, required: ['caseId'] }, outputSchema: { type: 'object', properties: { detected: { type: 'boolean' }, confidence: { type: 'number' }, movementChains: { type: 'array' } } } }, { name: 'analyze_data_exfiltration', description: 'Analyze potential data exfiltration', inputSchema: { type: 'object', properties: { caseId: { type: 'string' }, timeRange: { type: 'object' } }, required: ['caseId'] }, outputSchema: { type: 'object', properties: { suspiciousTransfers: { type: 'number' }, totalDataTransferred: { type: 'number' }, riskLevel: { type: 'string' } } } }, { name: 'detect_c2_communication', description: 'Detect command and control communication', inputSchema: { type: 'object', properties: { caseId: { type: 'string' }, indicators: { type: 'array' } }, required: ['caseId'] }, outputSchema: { type: 'object', properties: { detected: { type: 'boolean' }, confidence: { type: 'number' }, connections: { type: 'array' } } } } ]; return { id: { type: 'network', instance: 'primary', uuid: crypto.randomUUID() }, name: 'Network Analysis Agent', description: 'Advanced network traffic analysis and threat detection', version: '1.0.0', capabilities, dependencies: [], resources: { memory: 1024, cpu: 2 } }; } //# sourceMappingURL=network-agent.js.map