Files
Jonathan Miller 00d44256b4 refactor: rename MokoWaaS to MokoSuite across entire codebase
Rebrand all 17 sub-extensions from mokowaas to mokosuite naming,
including component, plugins, modules, task plugins, and webservices.
Updates package manifest, workflows, docs, wiki, and issue templates.
Adds new plg_system_mokosuite_license extension.
2026-06-07 09:25:45 -05:00

222 lines
8.1 KiB
PHP

<?php
/**
* @package MokoSuite
* @subpackage com_mokosuite
* @copyright Copyright (C) 2026 Moko Consulting. All rights reserved.
* @license GNU General Public License version 3 or later; see LICENSE
*/
defined('_JEXEC') or die;
use Joomla\CMS\Language\Text;
use Joomla\CMS\Router\Route;
use Joomla\CMS\Session\Session;
/** @var \Moko\Component\MokoSuite\Administrator\View\Extensions\HtmlView $this */
$packages = $this->packages;
$token = Session::getFormToken();
// Group by category
$grouped = [];
foreach ($packages as $pkg)
{
$grouped[$pkg->category][] = $pkg;
}
$statusBadge = [
'installed' => ['bg-success', 'Installed'],
'update_available' => ['bg-warning text-dark', 'Update Available'],
'not_installed' => ['bg-secondary', 'Not Installed'],
];
?>
<div id="mokosuite-extensions">
<div class="alert alert-info">
<span class="icon-info-circle" aria-hidden="true"></span>
<?php echo Text::_('COM_MOKOSUITE_EXTENSIONS_INFO'); ?>
</div>
<?php foreach ($grouped as $category => $pkgs): ?>
<h3 class="mb-3"><?php echo htmlspecialchars($category); ?></h3>
<div class="row g-3 mb-4">
<?php foreach ($pkgs as $pkg): ?>
<?php
$badge = $statusBadge[$pkg->status] ?? $statusBadge['not_installed'];
?>
<div class="col-12 <?php echo \count($pkgs) === 1 ? '' : (\count($pkgs) === 2 ? 'col-md-6' : 'col-md-6 col-xl-4'); ?>">
<div class="card h-100">
<div class="card-body d-flex flex-column">
<div class="d-flex align-items-start justify-content-between mb-2">
<div class="d-flex align-items-center gap-2">
<span class="<?php echo htmlspecialchars($pkg->icon); ?>" aria-hidden="true" style="font-size:1.5rem;color:#1a2744"></span>
<div>
<h5 class="card-title mb-0"><?php echo htmlspecialchars($pkg->label); ?></h5>
<small class="text-muted"><?php echo htmlspecialchars($pkg->type); ?></small>
</div>
</div>
<span class="badge <?php echo $badge[0]; ?>"><?php echo $badge[1]; ?></span>
</div>
<p class="card-text text-muted flex-grow-1"><?php echo htmlspecialchars($pkg->description); ?></p>
<?php if (!empty($pkg->needs_dlid) && !$pkg->has_dlid && $pkg->status !== 'not_installed'): ?>
<div class="alert alert-danger py-1 px-2 mb-2" style="font-size:0.8rem;">
<span class="icon-exclamation-triangle" aria-hidden="true"></span>
Download key missing — updates will fail.
<a href="index.php?option=com_installer&view=updatesites" class="alert-link">Configure</a>
</div>
<?php endif; ?>
<div class="d-flex align-items-center justify-content-between mt-auto pt-2 border-top">
<div class="small text-muted">
<?php if ($pkg->local_version): ?>
v<?php echo htmlspecialchars($pkg->local_version); ?>
<?php if ($pkg->remote_version && $pkg->status === 'update_available'): ?>
&rarr; <?php echo htmlspecialchars($pkg->remote_version); ?>
<?php endif; ?>
<?php elseif ($pkg->remote_version): ?>
Latest: <?php echo htmlspecialchars($pkg->remote_version); ?>
<?php endif; ?>
</div>
<div class="d-flex gap-1">
<?php if ($pkg->article_url): ?>
<a href="<?php echo htmlspecialchars($pkg->article_url); ?>" target="_blank" class="btn btn-sm btn-outline-secondary" title="Documentation">
<span class="icon-book" aria-hidden="true"></span>
</a>
<?php endif; ?>
<?php if ($pkg->download_url && $pkg->status === 'update_available'): ?>
<button type="button" class="btn btn-sm btn-warning mokosuite-install-btn"
data-url="<?php echo Route::_('index.php?option=com_mokosuite&task=display.installExtension&format=json'); ?>"
data-download="<?php echo htmlspecialchars($pkg->download_url); ?>"
data-token="<?php echo $token; ?>"
data-label="<?php echo htmlspecialchars($pkg->label); ?>"
data-needs-dlid="<?php echo $pkg->needs_dlid ? '1' : '0'; ?>"
data-element="<?php echo htmlspecialchars($pkg->element); ?>">
<span class="icon-refresh" aria-hidden="true"></span>
Update to <?php echo htmlspecialchars($pkg->remote_version); ?>
</button>
<?php elseif ($pkg->download_url && $pkg->status === 'not_installed'): ?>
<button type="button" class="btn btn-sm btn-primary mokosuite-install-btn"
data-url="<?php echo Route::_('index.php?option=com_mokosuite&task=display.installExtension&format=json'); ?>"
data-download="<?php echo htmlspecialchars($pkg->download_url); ?>"
data-token="<?php echo $token; ?>"
data-label="<?php echo htmlspecialchars($pkg->label); ?>"
data-needs-dlid="<?php echo $pkg->needs_dlid ? '1' : '0'; ?>"
data-element="<?php echo htmlspecialchars($pkg->element); ?>">
<span class="icon-download" aria-hidden="true"></span>
Install
</button>
<?php elseif ($pkg->status === 'installed'): ?>
<?php
$dashLink = '';
if ($pkg->type === 'component')
{
$dashLink = 'index.php?option=' . $pkg->element;
}
elseif ($pkg->type === 'package' && strpos($pkg->element, 'pkg_') === 0)
{
$comElement = 'com_' . substr($pkg->element, 4);
if (is_dir(JPATH_ADMINISTRATOR . '/components/' . $comElement))
{
$dashLink = 'index.php?option=' . $comElement;
}
}
?>
<?php if ($dashLink): ?>
<a href="<?php echo Route::_($dashLink); ?>" class="btn btn-sm btn-outline-primary" title="Open">
<span class="icon-arrow-right" aria-hidden="true"></span> Open
</a>
<?php endif; ?>
<span class="btn btn-sm btn-outline-success disabled">
<span class="icon-check" aria-hidden="true"></span> Installed
</span>
<?php if (!$pkg->protected && $pkg->extension_id): ?>
<a href="<?php echo Route::_('index.php?option=com_installer&task=manage.remove&cid[]=' . $pkg->extension_id . '&' . $token . '=1'); ?>"
class="btn btn-sm btn-outline-danger"
onclick="return confirm('Uninstall <?php echo htmlspecialchars($pkg->label); ?>?')"
title="Uninstall">
<span class="icon-times" aria-hidden="true"></span>
</a>
<?php endif; ?>
<?php else: ?>
<span class="btn btn-sm btn-outline-secondary disabled">No release</span>
<?php endif; ?>
</div>
</div>
</div>
</div>
</div>
<?php endforeach; ?>
</div>
<?php endforeach; ?>
</div>
<script>
document.addEventListener('DOMContentLoaded', function() {
document.querySelectorAll('.mokosuite-install-btn').forEach(function(btn) {
btn.addEventListener('click', function() {
var el = this;
var url = el.dataset.url;
var downloadUrl = el.dataset.download;
var token = el.dataset.token;
var label = el.dataset.label;
var needsDlid = el.dataset.needsDlid === '1';
var dlid = '';
if (needsDlid) {
dlid = prompt('Enter download key for ' + label + ':', '');
if (dlid === null) return;
if (!dlid.trim()) {
Joomla.renderMessages({error: ['Download key is required for ' + label]});
return;
}
}
if (!confirm('Install ' + label + '?')) return;
el.disabled = true;
var origHtml = el.textContent;
el.textContent = ' Installing...';
// Append dlid to download URL if provided
var finalUrl = downloadUrl;
if (dlid) {
finalUrl += (downloadUrl.indexOf('?') !== -1 ? '&' : '?') + 'dlid=' + encodeURIComponent(dlid.trim());
}
var fd = new FormData();
fd.append('download_url', finalUrl);
fd.append(token, '1');
if (dlid) {
fd.append('dlid', dlid.trim());
fd.append('element', el.dataset.element || '');
}
fetch(url, {
method: 'POST',
body: fd,
headers: {'X-Requested-With': 'XMLHttpRequest'}
})
.then(function(r) { return r.json(); })
.then(function(d) {
if (d.success) {
Joomla.renderMessages({message: [label + ': ' + d.message]});
location.reload();
} else {
Joomla.renderMessages({error: [label + ': ' + (d.message || 'Failed')]});
el.disabled = false;
el.textContent = origHtml;
}
})
.catch(function() {
Joomla.renderMessages({error: ['Network error']});
el.disabled = false;
el.textContent = origHtml;
});
});
});
});
</script>