diff --git a/source/packages/com_mokowaas/admin/src/Controller/DisplayController.php b/source/packages/com_mokowaas/admin/src/Controller/DisplayController.php index e8ecb437..ad76a4e2 100644 --- a/source/packages/com_mokowaas/admin/src/Controller/DisplayController.php +++ b/source/packages/com_mokowaas/admin/src/Controller/DisplayController.php @@ -80,6 +80,96 @@ class DisplayController extends BaseController } // ================================================================== + // Heartbeat + // ================================================================== + + public function sendHeartbeat() + { + Session::checkToken() or die(Text::_('JINVALID_TOKEN')); + + try + { + $monitorPlugin = \Joomla\CMS\Plugin\PluginHelper::getPlugin('system', 'mokowaas_monitor'); + + if (!$monitorPlugin) + { + $this->jsonResponse(['success' => false, 'message' => 'Monitor plugin not enabled.']); + + return; + } + + $params = new \Joomla\Registry\Registry($monitorPlugin->params); + $baseUrl = rtrim($params->get('base_url', ''), '/'); + + if (empty($baseUrl)) + { + $this->jsonResponse(['success' => false, 'message' => 'MokoWaaSBase URL not configured in monitor plugin.']); + + return; + } + + $corePlugin = \Joomla\CMS\Plugin\PluginHelper::getPlugin('system', 'mokowaas'); + $coreParams = new \Joomla\Registry\Registry($corePlugin ? $corePlugin->params : '{}'); + $healthToken = $coreParams->get('health_api_token', ''); + + if (empty($healthToken)) + { + $this->jsonResponse(['success' => false, 'message' => 'Health token not configured.']); + + return; + } + + $siteUrl = rtrim(\Joomla\CMS\Uri\Uri::root(), '/'); + $domain = parse_url($siteUrl, PHP_URL_HOST) ?: ''; + + $payload = json_encode([ + 'token' => $healthToken, + 'domain' => $domain, + 'site_name' => Factory::getConfig()->get('sitename', 'Joomla'), + 'site_url' => $siteUrl, + 'joomla_version' => (new \Joomla\CMS\Version())->getShortVersion(), + 'php_version' => PHP_VERSION, + ], JSON_UNESCAPED_SLASHES); + + $endpoint = $baseUrl . '/api/index.php/v1/mokowaasbase/heartbeat'; + + $ch = curl_init($endpoint); + curl_setopt_array($ch, [ + CURLOPT_POST => true, + CURLOPT_HTTPHEADER => ['Content-Type: application/json'], + CURLOPT_POSTFIELDS => $payload, + CURLOPT_RETURNTRANSFER => true, + CURLOPT_TIMEOUT => 15, + CURLOPT_FOLLOWLOCATION => true, + CURLOPT_SSL_VERIFYPEER => false, + ]); + + $response = curl_exec($ch); + $code = (int) curl_getinfo($ch, CURLINFO_HTTP_CODE); + $error = curl_error($ch); + curl_close($ch); + + if ($error) + { + $this->jsonResponse(['success' => false, 'message' => 'Connection failed: ' . $error]); + } + elseif ($code >= 200 && $code < 300) + { + $body = json_decode($response, true); + $this->jsonResponse(['success' => true, 'message' => 'Heartbeat sent: ' . ($body['status'] ?? 'ok')]); + } + else + { + $body = json_decode($response, true); + $this->jsonResponse(['success' => false, 'message' => 'HTTP ' . $code . ': ' . ($body['error'] ?? $body['message'] ?? 'Unknown')]); + } + } + catch (\Throwable $e) + { + $this->jsonResponse(['success' => false, 'message' => 'Error: ' . $e->getMessage()]); + } + } + // Cache // ================================================================== diff --git a/source/packages/plg_system_mokowaas/Field/CopyableTokenField.php b/source/packages/plg_system_mokowaas/Field/CopyableTokenField.php index 1b1725cf..cb320fc9 100644 --- a/source/packages/plg_system_mokowaas/Field/CopyableTokenField.php +++ b/source/packages/plg_system_mokowaas/Field/CopyableTokenField.php @@ -18,6 +18,7 @@ namespace Moko\Plugin\System\MokoWaaS\Field; defined('_JEXEC') or die; use Joomla\CMS\Form\FormField; +use Joomla\CMS\Session\Session; /** * Renders a read-only text input with a "Copy" button, similar to @@ -39,8 +40,9 @@ class CopyableTokenField extends FormField return '
Token will be generated automatically on first save.
'; } - // Derive a human-readable support PIN from the token - $pin = strtoupper(substr($this->value, 0, 4) . '-' . substr($this->value, 4, 4)); + $pin = strtoupper(substr($this->value, 0, 4) . '-' . substr($this->value, 4, 4)); + $token = Session::getFormToken(); + $ajaxUrl = 'index.php?option=com_mokowaas&task=display.sendHeartbeat&format=json'; return << @@ -60,6 +62,31 @@ class CopyableTokenField extends FormField inp.select(); document.execCommand('copy'); } "> Copy +
MOKO-{$pin}