From 6c61723146e272f8ce10d880d0d991767fdc82e8 Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Mon, 3 Jul 2023 18:13:40 +0200 Subject: [systemstatus] Add page to update/upgrade the server OS Some simple UI/buttons to run apt-get update, upgrade etc. --- modules-available/systemstatus/page.inc.php | 93 +++++++++++++++++++++++++++-- 1 file changed, 89 insertions(+), 4 deletions(-) (limited to 'modules-available/systemstatus/page.inc.php') diff --git a/modules-available/systemstatus/page.inc.php b/modules-available/systemstatus/page.inc.php index c25120f0..302e150d 100644 --- a/modules-available/systemstatus/page.inc.php +++ b/modules-available/systemstatus/page.inc.php @@ -3,6 +3,8 @@ class Page_SystemStatus extends Page { + const TM_UPDATE_UUID = '345-45763457-24356-234324556'; + protected function doPreprocess() { User::load(); @@ -13,14 +15,46 @@ class Page_SystemStatus extends Page } $action = Request::post('action', false, 'string'); - if ($action === 'reboot') { + $aptAction = null; + switch ($action) { + case 'reboot': User::assertPermission("serverreboot"); $task = Taskmanager::submit('Reboot'); if (Taskmanager::isTask($task)) { Util::redirect('?do=systemstatus&taskid=' . $task['id']); } - } elseif ($action === 'service-start' || $action === 'service-restart') { + break; + case 'service-start': + case 'service-restart': $this->handleServiceAction(substr($action, 8)); + break; + case 'apt-update': + User::assertPermission('apt.update'); + $aptAction = 'UPDATE'; + break; + case 'apt-upgrade': + User::assertPermission('apt.upgrade'); + $aptAction = 'UPGRADE'; + break; + case 'apt-full-upgrade': + User::assertPermission('apt.upgrade'); + $aptAction = 'FULL_UPGRADE'; + break; + case 'apt-autoremove': + User::assertPermission('apt.autoremove'); + $aptAction = 'AUTOREMOVE'; + break; + case 'apt-fix': + User::assertPermission('apt.fix'); + $aptAction = 'FIX'; + break; + } + if ($aptAction !== null) { + if (!Taskmanager::isRunning(Taskmanager::status(self::TM_UPDATE_UUID))) { + $task = Taskmanager::submit('AptUpgrade', ['mode' => $aptAction, 'id' => self::TM_UPDATE_UUID]); + Taskmanager::release($task); + } + Util::redirect('?do=systemstatus#id-ListUpgradable_pane'); } if (Request::isPost()) { Util::redirect('?do=systemstatus'); @@ -50,10 +84,11 @@ class Page_SystemStatus extends Page $data = array(); $data['taskid'] = Request::get('taskid', '', 'string'); $data['taskname'] = Request::get('taskname', 'Reboot', 'string'); - $tabs = array('DmsdLog', 'Netstat', 'PsList', 'LdadpLog', 'LighttpdLog', 'Dnbd3Log'); + $tabs = ['DmsdLog', 'Netstat', 'PsList', 'LdadpLog', 'LighttpdLog', 'Dnbd3Log', 'ListUpgradable']; $data['tabs'] = array(); // Dictionary::translate('tab_DmsdLog') Dictionary::translate('tab_LdadpLog') Dictionary::translate('tab_Netstat') // Dictionary::translate('tab_LighttpdLog') Dictionary::translate('tab_PsList') Dictionary::translate('tab_Dnbd3Log') + // Dictionary::translate('tab_ListUpgradable') foreach ($tabs as $tab) { $data['tabs'][] = array( 'type' => $tab, @@ -86,6 +121,56 @@ class Page_SystemStatus extends Page } } + protected function ajaxListUpgradable() + { + User::assertPermission("apt.*"); + + if (User::hasPermission('apt.update') + && Taskmanager::isRunning(Taskmanager::status(self::TM_UPDATE_UUID))) { + echo Render::parse('sys-update-update', [ + 'taskid' => self::TM_UPDATE_UUID, + 'rnd' => mt_rand(), + ]); + return; + } + + $task = Taskmanager::submit('AptGetUpgradable'); + + // Estimate last time package list was updated + $osRelease = parse_ini_file('/etc/os-release'); + $lastDownload = filemtime('/var/lib/apt/lists/partial'); + $lastChanged = 0; + foreach (glob('/var/lib/apt/lists/*_dists_' . ($osRelease['VERSION_CODENAME'] ?? '') . '*_InRelease', GLOB_NOSORT) as $f) { + $b = basename($f); + if (preg_match('/dists_[a-z]+(?:[\-_]updates)?_InRelease$/', $b)) { + $lastChanged = max($lastChanged, filemtime($f)); + } + } + + $perms = []; + Permission::addGlobalTags($perms, 0, ['apt.update', 'apt.upgrade', 'apt.autoremove', 'apt.fix']); + + if ($task !== false) { + $task = Taskmanager::waitComplete($task, 30000); + + if (Taskmanager::isFailed($task) || !Taskmanager::isFinished($task)) { + Taskmanager::addErrorMessage($task); + return; + } + if (!Taskmanager::isFailed($task) && empty($task['data']['packages'])) { + $task['data']['error'] = ''; + } + } + + echo Render::parse('sys-update-main', [ + 'task' => $task['data'], + 'lastDownload' => Util::prettyTime($lastDownload), + 'lastChanged' => Util::prettyTime($lastChanged), + 'perm' => $perms, + 'list_old' => $lastDownload + 86400 < time(), + ]); + } + protected function ajaxDiskStat() { User::assertPermission("show.overview.diskstat"); @@ -112,7 +197,7 @@ class Page_SystemStatus extends Page return; $task = Taskmanager::waitComplete($task, 3000); - if (!isset($task['data']['addresses']) || empty($task['data']['addresses'])) { + if (empty($task['data']['addresses'])) { Taskmanager::addErrorMessage($task); return; } -- cgit v1.2.3-55-g7522