post-processing enging * * @var array */ public $enginesPerProfile = []; /** * Should I show the browser download buttons in WordPress? * * @var bool * @since 7.6.1 */ public $showBrowserDownload; /** * Is PHP set up to output error to the browser? * * -1: Don't know; 0: no; 1 yes * * @var int * @since 7.6.1 */ public $phpErrorDisplay = -1; public function __construct($container = null) { parent::__construct($container); $this->lists = new \stdClass(); Template::addJs('media://js/solo/manage.js', $this->container->application); } public function onBeforeMain() { $user = $this->container->userManager->getUser(); $this->privileges['backup'] = $user->getPrivilege('akeeba.backup'); $this->privileges['download'] = $user->getPrivilege('akeeba.download'); $this->privileges['configure'] = $user->getPrivilege('akeeba.configure'); $document = $this->container->application->getDocument(); $router = $this->container->router; $task = $this->container->segment->get('solo_manage_task', 'main'); /** @var \Solo\Model\Manage $model */ $model = $this->getModel(); $this->lists->order = $model->getState('filter_order', 'backupstart'); $this->lists->order_Dir = $model->getState('filter_order_Dir', 'DESC'); $this->lists->fltDescription = $model->getState('filter_description', null); $this->lists->fltFrom = $model->getState('filter_from', null); $this->lists->fltTo = $model->getState('filter_to', null); $this->lists->fltOrigin = $model->getState('filter_origin', null); $this->lists->fltProfile = $model->getState('filter_profile', null); $this->lists->fltFrozen = $model->getState('filter_frozen', null); $filters = $this->_getFilters(); $ordering = $this->_getOrdering(); $this->items = $model->getStatisticsListWithMeta(false, $filters, $ordering); $containerClone = clone $this->getContainer(); $containerClone['mvc_config'] = [ 'modelTemporaryInstance' => true, 'modelClearState' => true, 'modelClearInput' => true, ]; /** @var Profiles $profileModel */ $profileModel = Model::getInstance(null, 'Profiles', $containerClone); $this->profiles = $profileModel->get(true); $this->profilesList = []; $this->profilesList[] = Select::option('', '—'); if (!empty($this->profiles)) { foreach ($this->profiles as $profile) { $this->profilesList[] = Select::option($profile->id, $profile->description); } } $this->frozenList = [ Select::option('', '–' . Text::_('COM_AKEEBA_BUADMIN_LABEL_FROZEN_SELECT') . '–'), Select::option('1', Text::_('COM_AKEEBA_BUADMIN_LABEL_FROZEN_FROZEN')), Select::option('2', Text::_('COM_AKEEBA_BUADMIN_LABEL_FROZEN_UNFROZEN')), ]; $this->pagination = $model->getPagination($filters); // Date format $dateFormat = $this->container->appConfig->get('dateformat', ''); $dateFormat = trim($dateFormat); $this->dateFormat = !empty($dateFormat) ? $dateFormat : Text::_('DATE_FORMAT_LC4'); // Time zone options $this->useLocalTime = $this->container->appConfig->get('localtime', '1') == 1; $this->timeZoneFormat = $this->container->appConfig->get('timezonetext', 'T'); $this->enginesPerProfile = $model->getPostProcessingEnginePerProfile(); $this->showBrowserDownload = $this->container->appConfig->get('showBrowserDownload', 0) == 1; if (function_exists('ini_get')) { $this->phpErrorDisplay = (ini_get('display_errors') ?: 0) ? 1 : 0; } // "Show warning first" download button. Text::script('COM_AKEEBA_BUADMIN_LOG_DOWNLOAD_CONFIRM', false); $document->addScriptOptions('akeeba.Manage.downloadURL', $router->route('index.php?option=com_akeeba&view=Manage&task=download&format=raw')); $buttons = [ 'view' => [ 'task' => 'main', 'title' => 'COM_AKEEBA_BUADMIN_LOG_EDITCOMMENT', 'class' => 'akeeba-btn--grey', 'onClick' => 'akeeba.System.submitForm(\'showComment\')', 'icon' => 'akion-edit', ], 'discover' => [ 'task' => 'main', 'title' => 'COM_AKEEBA_DISCOVER', 'class' => 'akeeba-btn--grey', 'url' => $router->route('index.php?view=discover'), 'icon' => 'akion-search', ], 's3import' => [ 'task' => 'main', 'title' => 'COM_AKEEBA_S3IMPORT', 'class' => 'akeeba-btn--grey', 'url' => $router->route('index.php?view=s3import'), 'icon' => 'akion-ios-cloud-download', ], 'restore' => [ 'task' => '', 'title' => 'COM_AKEEBA_BUADMIN_LABEL_RESTORE', 'class' => 'akeeba-btn--teal', 'onClick' => 'akeeba.System.submitForm(\'restore\')', 'icon' => 'akion-android-open', ], 'deletefiles' => [ 'task' => 'main', 'title' => 'COM_AKEEBA_BUADMIN_LABEL_DELETEFILES', 'class' => 'akeeba-btn--orange', 'onClick' => 'akeeba.System.submitForm(\'deleteFiles\')', 'icon' => 'akion-trash-a', ], 'delete' => [ 'task' => '', 'title' => 'SOLO_MANAGE_BTN_DELETE', 'class' => 'akeeba-btn--red', 'onClick' => 'akeeba.System.submitForm(\'remove\')', 'icon' => 'akion-trash-b', ], ]; if (!$this->privileges['configure']) { unset($buttons['discover']); unset($buttons['s3import']); unset($buttons['restore']); } elseif (!AKEEBABACKUP_PRO) { unset($buttons['restore']); unset($buttons['discover']); unset($buttons['s3import']); } if (!$this->privileges['backup']) { unset($buttons['delete']); unset($buttons['deletefiles']); } $toolbar = $document->getToolbar(); foreach ($buttons as $button) { if (empty($button['task']) || ($button['task'] == $task)) { $toolbar->addButtonFromDefinition($button); } } // Should I show the prompt for the configuration wizard? $this->promptForBackupRestoration = Platform::getInstance()->get_platform_configuration_option('show_howtorestoremodal', 1); // "Show warning first" download button. $confirmationText = Escape::escapeJS(Text::_('COM_AKEEBA_BUADMIN_LOG_DOWNLOAD_CONFIRM')); $confirmationText = str_replace('\\\\n', '\\n', $confirmationText); $newURL = Escape::escapeJS($router->route('index.php?view=manage&task=download&format=raw')); $js = <<getContainer()->application->getDocument()->addScriptDeclaration($js); // All done, show the page! return true; } public function onBeforeShowComment() { $model = $this->getModel(); $this->record_id = $model->getState('id', -1, 'int'); $this->record = Platform::getInstance()->get_statistics($this->record_id); $buttons = [ [ 'title' => 'SOLO_BTN_SAVECLOSE', 'class' => 'akeeba-btn--green', 'onClick' => 'akeeba.System.submitForm(\'save\')', 'icon' => 'akion-checkmark-circled', ], [ 'title' => 'SOLO_BTN_CANCEL', 'class' => 'akeeba-btn--orange', 'onClick' => 'akeeba.System.submitForm(\'cancel\')', 'icon' => 'akion-close-circled', ], ]; $toolbar = $this->container->application->getDocument()->getToolbar(); foreach ($buttons as $button) { $toolbar->addButtonFromDefinition($button); } return true; } /** * Translates the internal backup type (e.g. cli) to a human readable string * * @param string $recordType The internal backup type * * @return string */ public function translateBackupType($recordType) { static $backup_types = null; if (!is_array($backup_types)) { // Load a mapping of backup types to textual representation $scripting = Factory::getEngineParamsProvider()->loadScripting(); $backup_types = []; foreach ($scripting['scripts'] as $key => $data) { $backup_types[$key] = Text::_($data['text']); } } if (array_key_exists($recordType, $backup_types)) { return $backup_types[$recordType]; } return '–'; } /** * Get the start time and duration of a backup record * * @param array $record A backup record * * @return array array(startTimeAsString, durationAsString) */ protected function getTimeInformation($record) { $utcTimeZone = new DateTimeZone('UTC'); $startTime = new Date($record['backupstart'], $utcTimeZone); $endTime = new Date($record['backupend'], $utcTimeZone); $duration = $endTime->toUnix() - $startTime->toUnix(); if ($duration > 0) { $seconds = $duration % 60; $duration = $duration - $seconds; $minutes = ($duration % 3600) / 60; $duration = $duration - $minutes * 60; $hours = $duration / 3600; $duration = sprintf('%02d', $hours) . ':' . sprintf('%02d', $minutes) . ':' . sprintf('%02d', $seconds); } else { $duration = ''; } $tz = $this->container->appConfig->get('timezone', 'UTC'); $user = $this->container->userManager->getUser(); $user_tz = $user->getParameters()->get('timezone', null); if (!empty($user_tz)) { $tz = $user_tz; } $tzObject = new DateTimeZone($tz); $startTime->setTimezone($tzObject); $timeZoneSuffix = ''; if (!empty($this->timeZoneFormat)) { $timeZoneSuffix = $startTime->format($this->timeZoneFormat, $this->useLocalTime); } return [ $startTime->format($this->dateFormat, $this->useLocalTime), $duration, $timeZoneSuffix, ]; } /** * Get the class and icon for the backup status indicator * * @param array $record A backup record * * @return array array(class, icon) */ protected function getStatusInformation($record) { $statusClass = ''; switch ($record['meta']) { case 'ok': $statusIcon = 'akion-checkmark'; $statusClass = 'akeeba-label--green'; break; case 'pending': $statusIcon = 'akion-play'; $statusClass = 'akeeba-label--orange'; break; case 'fail': $statusIcon = 'akion-android-cancel'; $statusClass = 'akeeba-label--red'; break; case 'remote': $statusIcon = 'akion-cloud'; $statusClass = 'akeeba-label--teal'; break; default: $statusIcon = 'akion-trash-a'; $statusClass = 'akeeba-label--grey'; break; } return [$statusClass, $statusIcon]; } /** * Get the profile name for the backup record (or "–" if the profile no longer exists) * * @param array $record A backup record * * @return string */ protected function getProfileName($record) { $profileName = '—'; if (isset($this->profiles[$record['profile_id']])) { $profileName = $this->escape($this->profiles[$record['profile_id']]->description); return $profileName; } return $profileName; } /** * Returns the origin's translated name and the appropriate icon class * * @param array $record A backup record * * @return array array(originTranslation, iconClass) */ protected function getOriginInformation($record) { $originLanguageKey = 'COM_AKEEBA_BUADMIN_LABEL_ORIGIN_' . $record['origin']; $originDescription = Text::_($originLanguageKey); switch (strtolower($record['origin'])) { case 'backend': $originIcon = 'akion-android-desktop'; break; case 'frontend': $originIcon = 'akion-ios-world'; break; case 'json': $originIcon = 'akion-android-cloud'; break; case 'cli': $originIcon = 'akion-ios-paper-outline'; break; default: $originIcon = 'akion-help'; break; } if (empty($originLanguageKey) || ($originDescription == $originLanguageKey)) { $originDescription = '–'; $originIcon = 'akion-help'; return [$originDescription, $originIcon]; } return [$originDescription, $originIcon]; } private function _getFilters() { $filters = []; $task = $this->container->segment->get('solo_manage_task', 'main'); if ($this->lists->fltDescription) { $filters[] = [ 'field' => 'description', 'operand' => 'LIKE', 'value' => $this->lists->fltDescription, ]; } if ($this->lists->fltFrom && $this->lists->fltTo) { $filters[] = [ 'field' => 'backupstart', 'operand' => 'BETWEEN', 'value' => $this->lists->fltFrom, 'value2' => $this->lists->fltTo, ]; } elseif ($this->lists->fltFrom) { $filters[] = [ 'field' => 'backupstart', 'operand' => '>=', 'value' => $this->lists->fltFrom, ]; } elseif ($this->lists->fltTo) { $filters[] = [ 'field' => 'backupstart', 'operand' => '<=', 'value' => $this->lists->fltTo, ]; } if ($this->lists->fltOrigin) { $filters[] = [ 'field' => 'origin', 'operand' => '=', 'value' => $this->lists->fltOrigin, ]; } if ($this->lists->fltProfile) { $filters[] = [ 'field' => 'profile_id', 'operand' => '=', 'value' => (int) $this->lists->fltProfile, ]; } if ($this->lists->fltFrozen == 1) { $filters[] = [ 'field' => 'frozen', 'operand' => '=', 'value' => 1, ]; } elseif ($this->lists->fltFrozen == 2) { $filters[] = [ 'field' => 'frozen', 'operand' => '=', 'value' => 0, ]; } if (empty($filters)) { $filters = null; } return $filters; } private function _getOrdering() { $order = [ 'by' => $this->lists->order, 'order' => strtoupper($this->lists->order_Dir), ]; return $order; } }