'Weval Mind Core', 'hamid' => 'HAMID IA Engine', 'brain' => 'Brain Engine', 'perception' => 'Perception Module', 'diagnostic' => 'Diagnostic Module', 'planning' => 'Planning Module', 'execution' => 'Execution Module', 'learning' => 'Learning Module', 'surgeon' => 'Auto-Surgeon', 'reputation' => 'Reputation Monitor', 'alert' => 'Alert System' ]; public function __construct() { $this->db = getDB(); $this->initRateLimiting(); } /** * Initialize rate limiting */ private function initRateLimiting() { $clientIp = $this->getClientIp(); $minute = date('Y-m-d H:i'); // Simple in-memory rate limiting (for demo) // In production, use Redis or database $this->rateLimit[$clientIp][$minute] = ($this->rateLimit[$clientIp][$minute] ?? 0) + 1; } /** * Check rate limiting */ private function checkRateLimit($clientIp) { $minute = date('Y-m-d H:i'); $requests = $this->rateLimit[$clientIp][$minute] ?? 0; if ($requests > 60) { logMessage('WARNING', 'API Gateway', 'Rate limit exceeded', [ 'ip' => $clientIp, 'requests' => $requests ]); return false; } return true; } /** * Get client IP */ private function getClientIp() { $ip = $_SERVER['HTTP_X_FORWARDED_FOR'] ?? $_SERVER['HTTP_CLIENT_IP'] ?? $_SERVER['REMOTE_ADDR'] ?? '0.0.0.0'; return $ip; } /** * Authenticate request */ private function authenticate() { // Check for API key in headers $apiKey = $_SERVER['HTTP_X_API_KEY'] ?? $_GET['api_key'] ?? $_POST['api_key'] ?? null; // Check for session (if coming from Arsenal frontend) $sessionId = $_COOKIE['arsenal_session'] ?? null; // For now, allow all requests (in production, implement proper auth) return true; } /** * Route request to appropriate module */ private function routeRequest($module, $action, $data) { switch ($module) { case 'mind': return $this->routeToMind($action, $data); case 'hamid': return $this->routeToHamid($action, $data); case 'status': return $this->getSystemStatus(); case 'health': return $this->healthCheck(); default: return [ 'error' => 'Module not found', 'available_modules' => array_keys($this->modules) ]; } } /** * Route to Weval Mind */ private function routeToMind($action, $data) { // For now, redirect to existing simple API // Later, this will call the full Weval Mind Core $validActions = ['autonomous_cycle', 'status', 'emergency', 'diagnose', 'report']; if (!in_array($action, $validActions)) { return [ 'error' => 'Invalid action for mind module', 'valid_actions' => $validActions ]; } // Call the simple API we already have if ($action === 'autonomous_cycle') { $result = $this->callSimpleApi('weval-mind-core-simple.php', [ 'action' => 'autonomous_cycle' ]); // Log the cycle if (isset($result['cycle_id'])) { $this->logCycle($result); } return $result; } return [ 'module' => 'mind', 'action' => $action, 'status' => 'processing', 'message' => 'Action queued for execution' ]; } /** * Route to HAMID IA */ private function routeToHamid($action, $data) { $validActions = ['chat', 'providers', 'stats', 'kb_search', 'kb_add']; if (!in_array($action, $validActions)) { return [ 'error' => 'Invalid action for hamid module', 'valid_actions' => $validActions ]; } if ($action === 'chat') { if (empty($data['message'])) { return ['error' => 'Message is required for chat action']; } // For now, use the simple interface // Later, this will call the full HAMID Engine return [ 'response' => "HAMID IA Engine is under construction. Your message: " . htmlspecialchars(substr($data['message'], 0, 100)), 'provider' => 'gateway', 'action' => 'chat', 'note' => 'Full HAMID Engine coming soon' ]; } return [ 'module' => 'hamid', 'action' => $action, 'status' => 'available_soon', 'message' => 'HAMID Engine module in development' ]; } /** * Get system status */ private function getSystemStatus() { try { $dbHealth = $this->db->healthCheck(); // Check if services are running $services = [ 'apache' => $this->checkService('apache2'), 'postgresql' => $this->checkService('postgresql'), 'pmta' => $this->checkService('pmta') ]; // Get system metrics $load = sys_getloadavg(); $memory = shell_exec("free -m | awk 'NR==2 {printf \"%.1f\", $3/$2*100}'"); $disk = shell_exec("df / | awk 'NR==2 {print $5}' | sed 's/%//'"); return [ 'status' => 'operational', 'timestamp' => date('Y-m-d H:i:s'), 'services' => $services, 'metrics' => [ 'cpu_load' => [ '1min' => $load[0] ?? 0, '5min' => $load[1] ?? 0, '15min' => $load[2] ?? 0 ], 'memory_usage' => floatval($memory) ?: 0, 'disk_usage' => floatval($disk) ?: 0 ], 'database' => $dbHealth, 'modules' => $this->modules, 'environment' => ENVIRONMENT ]; } catch (Exception $e) { return [ 'status' => 'degraded', 'error' => $e->getMessage(), 'timestamp' => date('Y-m-d H:i:s') ]; } } /** * Health check */ private function healthCheck() { $checks = []; // Check database try { $dbCheck = $this->db->healthCheck(); $checks['database'] = [ 'status' => $dbCheck['status'], 'query_count' => $dbCheck['query_count'] ]; } catch (Exception $e) { $checks['database'] = [ 'status' => 'unhealthy', 'error' => $e->getMessage() ]; } // Check services $services = ['apache2', 'postgresql', 'pmta']; foreach ($services as $service) { $checks['service_' . $service] = [ 'status' => $this->checkService($service) ? 'running' : 'stopped' ]; } // Check disk space $disk = shell_exec("df / | awk 'NR==2 {print $5}' | sed 's/%//'"); $checks['disk_space'] = [ 'usage_percent' => floatval($disk) ?: 0, 'status' => (floatval($disk) > 85) ? 'warning' : 'healthy' ]; // Determine overall status $overall = 'healthy'; foreach ($checks as $check) { if (isset($check['status']) && $check['status'] === 'unhealthy') { $overall = 'unhealthy'; break; } if (isset($check['status']) && $check['status'] === 'warning') { $overall = 'warning'; } } return [ 'status' => $overall, 'checks' => $checks, 'timestamp' => date('Y-m-d H:i:s'), 'uptime' => shell_exec("uptime -p 2>/dev/null || echo 'unknown'") ]; } /** * Call simple API */ private function callSimpleApi($endpoint, $params = []) { $url = "http://localhost:5890/api/$endpoint"; if (!empty($params)) { $url .= '?' . http_build_query($params); } $response = @file_get_contents($url); if ($response === false) { return ['error' => 'Failed to call API endpoint: ' . $endpoint]; } $data = json_decode($response, true); return $data ?: ['error' => 'Invalid JSON response']; } /** * Check if service is running */ private function checkService($service) { $status = @shell_exec("systemctl is-active $service 2>/dev/null"); return trim($status) === 'active'; } /** * Log cycle to database */ private function logCycle($cycleData) { try { $cycleId = $this->db->insert('mind_cycles', [ 'cycle_uuid' => $cycleData['cycle_id'] ?? 'CYCLE-' . uniqid(), 'trigger_type' => 'api_gateway', 'started_at' => $cycleData['timestamp'] ?? date('Y-m-d H:i:s'), 'ended_at' => date('Y-m-d H:i:s'), 'status' => 'completed', 'health_score' => 95, // Default for now 'issues_found' => 0, 'actions_taken' => 0, 'modules_run' => ['perception'], 'result_json' => json_encode($cycleData) ]); logMessage('INFO', 'API Gateway', 'Cycle logged to database', [ 'cycle_id' => $cycleId, 'uuid' => $cycleData['cycle_id'] ?? 'unknown' ]); } catch (Exception $e) { logMessage('ERROR', 'API Gateway', 'Failed to log cycle: ' . $e->getMessage()); } } /** * Process incoming request */ public function processRequest() { try { // Get request data $method = $_SERVER['REQUEST_METHOD']; $clientIp = $this->getClientIp(); // Handle preflight requests if ($method === 'OPTIONS') { http_response_code(200); exit; } // Rate limiting if (!$this->checkRateLimit($clientIp)) { http_response_code(429); echo json_encode([ 'error' => 'Rate limit exceeded', 'limit' => 60 . ' requests per minute', 'retry_after' => 60 ]); exit; } // Authentication if (!$this->authenticate()) { http_response_code(401); echo json_encode(['error' => 'Authentication required']); exit; } // Get module and action $module = $_GET['module'] ?? $_POST['module'] ?? 'status'; $action = $_GET['action'] ?? $_POST['action'] ?? 'status'; // Get request data $input = file_get_contents('php://input'); $data = json_decode($input, true); if (json_last_error() !== JSON_ERROR_NONE) { $data = $_POST ?: []; } // Log the request logMessage('INFO', 'API Gateway', 'Request received', [ 'module' => $module, 'action' => $action, 'ip' => $clientIp, 'method' => $method ]); // Route the request $result = $this->routeRequest($module, $action, $data); // Add metadata $result['gateway'] = [ 'version' => '1.0', 'timestamp' => date('Y-m-d H:i:s'), 'request_id' => 'REQ-' . uniqid() ]; // Return response http_response_code(200); echo json_encode($result, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE); } catch (Exception $e) { logMessage('ERROR', 'API Gateway', 'Processing error: ' . $e->getMessage()); http_response_code(500); echo json_encode([ 'error' => 'Internal server error', 'message' => $e->getMessage(), 'timestamp' => date('Y-m-d H:i:s') ]); } } } // Handle request $gateway = new ApiGateway(); $gateway->processRequest(); ?>