refactor: remove 12 dead method bodies from core plugin (-607 lines)

Removed: resetAllHits, deleteAllVersions, warnMissingLicenseKey,
enforceDevMode, onDevModeDisabled, enforceHttps,
enforceAdminSessionTimeout, ipIsTrusted, enforceUploadRestrictions,
enforceAdminRestrictions, blockAccess, getHiddenMenuComponents

These methods were already unreachable after the call sites were
removed in the previous commit. The functionality lives in the
firewall, tenant, and devtools feature plugins.

Core plugin: 5366 -> 4759 lines

Authored-by: Moko Consulting
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Jonathan Miller
2026-06-02 14:33:57 -05:00
parent 1ad1f1c010
commit 9a375740b9
@@ -807,7 +807,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
return $strings;
}
/**
* Event triggered after an extension's config is saved.
*
@@ -935,48 +934,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
}
}
/**
* Reset all article hit counters to zero.
*
* @return int Number of rows affected
*
* @since 02.01.08
*/
protected function resetAllHits()
{
$db = Factory::getDbo();
$db->setQuery(
$db->getQuery(true)
->update($db->quoteName('#__content'))
->set($db->quoteName('hits') . ' = 0')
->where($db->quoteName('hits') . ' > 0')
);
$db->execute();
return $db->getAffectedRows();
}
/**
* Delete all content version history records.
*
* @return int Number of rows deleted
*
* @since 02.01.08
*/
protected function deleteAllVersions()
{
$db = Factory::getDbo();
$db->setQuery(
$db->getQuery(true)
->delete($db->quoteName('#__history'))
);
$db->execute();
return $db->getAffectedRows();
}
/**
* Event triggered after the route has been determined.
*
@@ -1513,7 +1470,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
// onPreprocessMenuItems — REMOVED, now in plg_system_mokowaas_tenant
// onUserBeforeSave — REMOVED, now in plg_system_mokowaas_firewall
// ------------------------------------------------------------------
// Diagnostics / Health Endpoint (called from onAfterInitialise)
// ------------------------------------------------------------------
@@ -4279,130 +4235,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
// License key check (called from onAfterRoute)
// ------------------------------------------------------------------
/**
* Show a persistent admin warning if no license key is set on the
* MokoWaaS update site.
*
* Checks the extra_query column in #__update_sites for a dlid value.
* Also validates the key against MokoGitea on a heartbeat interval
* (once per day) and warns if the key is invalid or expired.
*
* @return void
*
* @since 02.31.00
*/
protected function warnMissingLicenseKey(): void
{
// Only show to master users
if (!$this->isMasterUser())
{
return;
}
// Only warn once per session
$session = Factory::getSession();
if ($session->get('mokowaas.license_warned', false))
{
return;
}
$session->set('mokowaas.license_warned', true);
try
{
$db = Factory::getDbo();
$query = $db->getQuery(true)
->select($db->quoteName('extra_query'))
->from($db->quoteName('#__update_sites'))
->where('(' . $db->quoteName('name') . ' LIKE ' . $db->quote('%MokoWaaS%')
. ' OR ' . $db->quoteName('location') . ' LIKE ' . $db->quote('%MokoWaaS%') . ')')
->setLimit(1);
$db->setQuery($query);
$extraQuery = (string) $db->loadResult();
if (empty($extraQuery) || strpos($extraQuery, 'dlid=') === false)
{
$this->app->enqueueMessage(
'<strong>Moko Consulting License Key Required</strong> — '
. 'No download key is configured. Updates will not be available until a valid license key is entered. '
. 'Go to <a href="index.php?option=com_installer&view=updatesites">System → Update Sites</a> '
. 'and enter your license key in the Download Key field for the MokoWaaS update site.',
'warning'
);
return;
}
// Extract the key value from extra_query
parse_str($extraQuery, $parsed);
$licenseKey = $parsed['dlid'] ?? '';
if (empty($licenseKey))
{
return;
}
// Heartbeat validation — check once per day
$session = Factory::getSession();
$lastCheck = (int) $session->get('mokowaas.license_check', 0);
$now = time();
if (($now - $lastCheck) < 86400)
{
// Show cached warning if key was invalid last check
if ($session->get('mokowaas.license_invalid', false))
{
$this->app->enqueueMessage(
'<strong>Moko Consulting License Key Invalid</strong> — '
. 'Your license key could not be validated. Please verify your key in '
. '<a href="index.php?option=com_installer&view=updatesites">System → Update Sites</a>.',
'error'
);
}
return;
}
// Validate against MokoGitea
$session->set('mokowaas.license_check', $now);
$validateUrl = 'https://git.mokoconsulting.tech/MokoConsulting/MokoWaaS/updates.xml'
. '?dlid=' . urlencode($licenseKey)
. '&domain=' . urlencode(Uri::root());
$ch = curl_init($validateUrl);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 10);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$response = curl_exec($ch);
$httpCode = (int) curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
// Empty <updates></updates> or non-200 means invalid key
$isValid = ($httpCode === 200 && $response && strpos($response, '<update>') !== false);
$session->set('mokowaas.license_invalid', !$isValid);
if (!$isValid)
{
$this->app->enqueueMessage(
'<strong>Moko Consulting License Key Invalid</strong> — '
. 'Your license key could not be validated. Updates will not be available. '
. 'Please verify your key in '
. '<a href="index.php?option=com_installer&view=updatesites">System → Update Sites</a>.',
'error'
);
}
}
catch (\Throwable $e)
{
// Silent — license check is non-critical
}
}
// ------------------------------------------------------------------
/**
@@ -4538,110 +4370,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
*
* @since 02.01.08
*/
/**
* Enforce development mode settings.
*
* When dev mode is ON:
* - Disable Joomla caching
* - Enable Joomla debug mode (Global Config)
* - Enable MokoOnyx template debug
* - Disable article hit recording
*
* When dev mode is OFF (and was previously on):
* - Reset all content version history
* - Reset article published dates to now
*
* @return void
*
* @since 02.01.15
*/
protected function enforceDevMode()
{
if (!$this->params->get('dev_mode', 0))
{
return;
}
// Disable caching
$config = Factory::getConfig();
$config->set('caching', 0);
// Enable Joomla debug
$config->set('debug', 1);
// Enable MokoOnyx template debug
$this->setTemplateParam('mokoonyx', 'debug', 1);
// Show offline page on primary domain only — site aliases
// and dev.* subdomains bypass offline mode for development
$currentHost = $_SERVER['HTTP_HOST'] ?? '';
$primaryDomain = $this->params->get('primary_domain', '');
if (!empty($primaryDomain) && $currentHost === $primaryDomain)
{
$config->set('offline', 1);
}
// Suppress hit recording
try
{
$db = Factory::getDbo();
$db->setQuery(
$db->getQuery(true)
->update($db->quoteName('#__content'))
->set($db->quoteName('hits') . ' = 0')
->where($db->quoteName('hits') . ' > 0')
)->execute();
}
catch (\Throwable $e)
{
// Silent
}
}
/**
* Actions to run when dev mode is turned off.
*
* Resets content versions and hits, disables debug.
*
* @return void
*
* @since 02.31.00
*/
protected function onDevModeDisabled(): void
{
try
{
$db = Factory::getDbo();
// Delete all content version history
$db->setQuery(
$db->getQuery(true)->delete($db->quoteName('#__history'))
)->execute();
// Reset hits
$db->setQuery(
$db->getQuery(true)
->update($db->quoteName('#__content'))
->set($db->quoteName('hits') . ' = 0')
)->execute();
// Disable debug
$this->setTemplateParam('mokoonyx', 'debug', 0);
// Take site back online
Factory::getConfig()->set('offline', 0);
$this->app->enqueueMessage(
'Development mode disabled — versions cleared, hits reset, debug off, site online.',
'message'
);
}
catch (\Throwable $e)
{
Log::add('Dev mode cleanup failed: ' . $e->getMessage(), Log::WARNING, 'mokowaas');
}
}
/**
* Set a parameter on a template style.
@@ -4689,194 +4417,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
}
}
protected function enforceHttps()
{
if (!$this->params->get('force_https', 0))
{
return;
}
if ($this->app->isClient('cli'))
{
return;
}
$isHttps = (!empty($_SERVER['HTTPS'])
&& $_SERVER['HTTPS'] !== 'off')
|| ($_SERVER['HTTP_X_FORWARDED_PROTO'] ?? '') === 'https';
if (!$isHttps)
{
$this->app->redirect(
'https://' . $_SERVER['HTTP_HOST']
. $_SERVER['REQUEST_URI'], 301
);
}
}
/**
* Enforce admin session idle timeout.
*
* @return void
*
* @since 02.01.08
*/
protected function enforceAdminSessionTimeout()
{
$timeout = (int) $this->params->get('admin_session_timeout', 0);
if ($timeout <= 0)
{
return;
}
// Don't timeout the master user
if ($this->isMasterUser())
{
return;
}
// Trusted IPs — session lifetime already extended in boot()
if ($this->ipIsTrusted())
{
return;
}
$session = Factory::getSession();
$lastHit = $session->get('mokowaas.last_activity', 0);
$now = time();
if ($lastHit > 0 && ($now - $lastHit) > ($timeout * 60))
{
$this->app->logout();
$this->app->redirect(
Route::_('index.php', false)
);
return;
}
$session->set('mokowaas.last_activity', $now);
}
/**
* Check whether the current request IP matches any trusted IP entry.
*
* Supports exact IPs, CIDR notation (e.g. 10.0.0.0/8), and
* wildcard patterns (e.g. 192.168.1.*).
*
* @return bool True if the current IP is in the trusted list.
*
* @since 02.11.00
*/
protected function ipIsTrusted(): bool
{
$entries = $this->params->get('trusted_ips', '');
if (empty($entries))
{
return false;
}
// Subform stores as JSON string or array
if (\is_string($entries))
{
$entries = json_decode($entries, true);
}
if (!\is_array($entries))
{
return false;
}
$ip = $this->app
? $this->app->input->server->getString('REMOTE_ADDR', '')
: ($_SERVER['REMOTE_ADDR'] ?? '');
$ipLong = ip2long($ip);
if ($ipLong === false)
{
return false;
}
foreach ($entries as $entry)
{
if (empty($entry['enabled']) || empty($entry['ip']))
{
continue;
}
$range = trim($entry['ip']);
// Wildcard: 192.168.1.*
if (str_contains($range, '*'))
{
$pattern = '/^' . str_replace(['.', '*'], ['\\.', '\\d+'], $range) . '$/';
if (preg_match($pattern, $ip))
{
return true;
}
continue;
}
// CIDR: 10.0.0.0/8
if (str_contains($range, '/'))
{
[$subnet, $bits] = explode('/', $range, 2);
$subnetLong = ip2long($subnet);
$mask = -1 << (32 - (int) $bits);
if ($subnetLong !== false && ($ipLong & $mask) === ($subnetLong & $mask))
{
return true;
}
continue;
}
// Exact match
if ($ip === $range)
{
return true;
}
}
return false;
}
/**
* Override Joomla upload restrictions at runtime.
*
* @return void
*
* @since 02.01.08
*/
protected function enforceUploadRestrictions()
{
$types = $this->params->get('upload_allowed_types', '');
$maxMb = (int) $this->params->get('upload_max_size_mb', 0);
if (empty($types) && $maxMb <= 0)
{
return;
}
$config = $this->app->getConfig();
if (!empty($types))
{
$config->set('upload_extensions', $types);
}
if ($maxMb > 0)
{
$config->set('upload_maxsize', $maxMb);
}
}
/**
* Enforce login support module URLs on admin requests.
*
@@ -4945,121 +4485,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
// Tenant Restrictions (called from onAfterRoute)
// ------------------------------------------------------------------
/**
* Check admin routes against restriction rules and redirect if blocked.
*
* @return void
*
* @since 02.01.08
*/
protected function enforceAdminRestrictions()
{
// Master user bypasses ALL restrictions
if ($this->isMasterUser())
{
return;
}
$input = $this->app->input;
$option = $input->get('option', '');
$view = $input->get('view', '');
$task = $input->get('task', '');
// Disable install-from-URL for non-master users
if ($this->params->get('disable_install_url', 1)
&& $option === 'com_installer'
&& stripos($task, 'install') !== false
&& $input->get('installtype') === 'url')
{
$this->blockAccess('Install from URL is disabled.');
return;
}
$blocked = [];
if ($this->params->get('restrict_installer', 1))
{
// Allow the update view by default so tenants can update extensions
$allowUpdates = (int) $this->params->get('allow_extension_updates', 1);
if ($allowUpdates && $option === 'com_installer'
&& \in_array($view, ['update', 'updatesites'], true))
{
// Do not block — update views are permitted
}
elseif ($option === 'com_installer')
{
$this->blockAccess('Access restricted.');
return;
}
}
if ($this->params->get('hide_sysinfo', 1))
{
$blocked[] = [
'option' => 'com_admin',
'view' => 'sysinfo',
];
}
if ($this->params->get('restrict_global_config', 1))
{
$blocked[] = [
'option' => 'com_config',
'view' => 'application',
];
// Also block empty view (default landing = global config)
if ($option === 'com_config' && $view === '')
{
$this->blockAccess('Access restricted.');
return;
}
}
if ($this->params->get('restrict_template_editing', 1))
{
$blocked[] = [
'option' => 'com_templates',
'view' => 'template',
];
}
foreach ($blocked as $rule)
{
if ($option !== $rule['option'])
{
continue;
}
if (isset($rule['view']) && $view !== $rule['view'])
{
continue;
}
$this->blockAccess('Access restricted.');
return;
}
}
/**
* Redirect to admin dashboard with an error message.
*
* @param string $message Error message to display
*
* @return void
*
* @since 02.01.08
*/
protected function blockAccess($message)
{
$this->app->enqueueMessage($message, 'error');
$this->app->redirect(Route::_('index.php', false));
}
/**
* Check whether the current user is the master WaaS user.
*
@@ -5111,38 +4536,6 @@ class MokoWaaS extends CMSPlugin implements BootableExtensionInterface
return $this->masterNames;
}
/**
* Build the list of components to hide from admin menu.
*
* Combines explicit hidden_menu_items config with components that
* are implicitly blocked by other restriction toggles.
*
* @return array Component option strings
*
* @since 02.01.08
*/
protected function getHiddenMenuComponents()
{
$hidden = array_filter(array_map(
'trim',
explode("\n", $this->params->get('hidden_menu_items', ''))
));
// Auto-hide components that are restricted (keep visible when updates are allowed)
if ($this->params->get('restrict_installer', 1)
&& !$this->params->get('allow_extension_updates', 1))
{
$hidden[] = 'com_installer';
}
if ($this->params->get('hide_sysinfo', 1))
{
$hidden[] = 'com_admin';
}
return array_unique($hidden);
}
// ------------------------------------------------------------------
// Atum Template Branding (called from onAfterInitialise)
// ------------------------------------------------------------------