environment('production')) { throw new \RuntimeException('FATAL: rsx:ajax:debug command is not available in production environment. This is a development-only debugging tool.'); } // Get command arguments $controller = $this->argument('controller'); $action = $this->argument('action'); // Parse arguments if provided $args = []; if ($this->option('args')) { $args_json = $this->option('args'); $args = json_decode($args_json, true); if (json_last_error() !== JSON_ERROR_NONE) { $this->error('❌ Invalid JSON in --args parameter: ' . json_last_error_msg()); return 1; } } // Get user and site IDs $user_id = $this->option('user-id'); $site_id = $this->option('site-id'); // Rotate logs before test to ensure clean slate Debugger::logrotate(); // Set session context if provided if ($user_id !== null) { RsxSession::set_user_id((int)$user_id); $this->info("✓ Set user_id to {$user_id}"); } if ($site_id !== null) { RsxSession::set_site_id((int)$site_id); $this->info("✓ Set site_id to {$site_id}"); } // Show what we're calling $this->info(""); $this->info("Calling: {$controller}::{$action}"); if (!empty($args)) { $this->info("Arguments: " . json_encode($args, JSON_PRETTY_PRINT)); } $this->info(""); $this->line("─────────────────────────────────────────"); $this->info(""); try { // Call the Ajax method $response = Ajax::internal($controller, $action, $args); // Output successful response $this->info("✅ Success Response:"); $this->info(""); // Pretty print the JSON response $json_output = json_encode($response, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE); $this->line($json_output); } catch (AjaxAuthRequiredException $e) { // Handle auth required response $this->error("🔒 Authentication Required"); $this->error(""); $this->error("Login URL: " . $e->getMessage()); return 1; } catch (AjaxUnauthorizedException $e) { // Handle unauthorized response $this->error("⛔ Unauthorized"); $this->error(""); $this->error("Message: " . $e->getMessage()); return 1; } catch (AjaxFormErrorException $e) { // Handle form error response - format like /_ajax route $this->error("❌ Form Validation Error"); $this->error(""); $details = $e->get_details(); // Format the response like the /_ajax route does $formatted_response = [ 'success' => false, 'error' => $e->getMessage() ]; // Add any additional details from the exception if (!empty($details)) { foreach ($details as $key => $value) { if ($key !== 'message') { $formatted_response[$key] = $value; } } } $json_output = json_encode($formatted_response, JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE); $this->line($json_output); return 1; } catch (AjaxFatalErrorException $e) { // Handle fatal error response $this->error("💀 Fatal Error"); $this->error(""); $this->error("Message: " . $e->getMessage()); $this->error(""); $this->error("Stack Trace:"); $this->line($e->getTraceAsString()); return 1; } catch (\InvalidArgumentException $e) { // Handle invalid controller/action $this->error("❌ Invalid Request"); $this->error(""); $this->error($e->getMessage()); return 1; } catch (\Exception $e) { // Handle unexpected exceptions $this->error("💥 Unexpected Error"); $this->error(""); $this->error("Exception: " . get_class($e)); $this->error("Message: " . $e->getMessage()); $this->error(""); $this->error("Stack Trace:"); $this->line($e->getTraceAsString()); return 1; } // Rotate logs after test to clean slate for next run Debugger::logrotate(); return 0; } }