Feature: add a Server administration page

It contains mostly read only information about the current Shaarli instance,
PHP version, extensions, file and folder permissions, etc.
Also action buttons to clear the cache or sync thumbnails.

Part of the content of this page is also displayed on the install page,
to check server requirement before installing Shaarli config file.

Fixes 
Fixes 
This commit is contained in:
ArthurHoaro 2020-10-21 13:12:15 +02:00
parent d8030c8155
commit 0cf76ccb47
16 changed files with 1086 additions and 104 deletions

View file

@ -0,0 +1,87 @@
<?php
declare(strict_types=1);
namespace Shaarli\Front\Controller\Admin;
use Shaarli\ApplicationUtils;
use Shaarli\FileUtils;
use Slim\Http\Request;
use Slim\Http\Response;
/**
* Slim controller used to handle Server administration page, and actions.
*/
class ServerController extends ShaarliAdminController
{
/** @var string Cache type - main - by default pagecache/ and tmp/ */
protected const CACHE_MAIN = 'main';
/** @var string Cache type - thumbnails - by default cache/ */
protected const CACHE_THUMB = 'thumbnails';
/**
* GET /admin/server - Display page Server administration
*/
public function index(Request $request, Response $response): Response
{
$latestVersion = 'v' . ApplicationUtils::getVersion(
ApplicationUtils::$GIT_RAW_URL . '/latest/' . ApplicationUtils::$VERSION_FILE
);
$currentVersion = ApplicationUtils::getVersion('./shaarli_version.php');
$currentVersion = $currentVersion === 'dev' ? $currentVersion : 'v' . $currentVersion;
$phpEol = new \DateTimeImmutable(ApplicationUtils::getPhpEol(PHP_VERSION));
$this->assignView('php_version', PHP_VERSION);
$this->assignView('php_eol', format_date($phpEol, false));
$this->assignView('php_has_reached_eol', $phpEol < new \DateTimeImmutable());
$this->assignView('php_extensions', ApplicationUtils::getPhpExtensionsRequirement());
$this->assignView('permissions', ApplicationUtils::checkResourcePermissions($this->container->conf));
$this->assignView('release_url', ApplicationUtils::$GITHUB_URL . '/releases/tag/' . $latestVersion);
$this->assignView('latest_version', $latestVersion);
$this->assignView('current_version', $currentVersion);
$this->assignView('thumbnails_mode', $this->container->conf->get('thumbnails.mode'));
$this->assignView('index_url', index_url($this->container->environment));
$this->assignView('client_ip', client_ip_id($this->container->environment));
$this->assignView('trusted_proxies', $this->container->conf->get('security.trusted_proxies', []));
$this->assignView(
'pagetitle',
t('Server administration') . ' - ' . $this->container->conf->get('general.title', 'Shaarli')
);
return $response->write($this->render('server'));
}
/**
* GET /admin/clear-cache?type={$type} - Action to trigger cache folder clearing (either main or thumbnails).
*/
public function clearCache(Request $request, Response $response): Response
{
$exclude = ['.htaccess'];
if ($request->getQueryParam('type') === static::CACHE_THUMB) {
$folders = [$this->container->conf->get('resource.thumbnails_cache')];
$this->saveWarningMessage(
t('Thumbnails cache has been cleared.') . ' ' .
'<a href="'. $this->container->basePath .'/admin/thumbnails">' . t('Please synchronize them.') .'</a>'
);
} else {
$folders = [
$this->container->conf->get('resource.page_cache'),
$this->container->conf->get('resource.raintpl_tmp'),
];
$this->saveSuccessMessage(t('Shaarli\'s cache folder has been cleared!'));
}
// Make sure that we don't delete root cache folder
$folders = array_map('realpath', array_values(array_filter(array_map('trim', $folders))));
foreach ($folders as $folder) {
FileUtils::clearFolder($folder, false, $exclude);
}
return $this->redirect($response, '/admin/server');
}
}

View file

@ -169,16 +169,24 @@ class BookmarkListController extends ShaarliVisitorController
*/
protected function updateThumbnail(Bookmark $bookmark, bool $writeDatastore = true): bool
{
// Logged in, not async retrieval, thumbnails enabled, and thumbnail should be updated
if ($this->container->loginManager->isLoggedIn()
&& true !== $this->container->conf->get('general.enable_async_metadata', true)
&& $this->container->conf->get('thumbnails.mode', Thumbnailer::MODE_NONE) !== Thumbnailer::MODE_NONE
&& $bookmark->shouldUpdateThumbnail()
) {
$bookmark->setThumbnail($this->container->thumbnailer->get($bookmark->getUrl()));
$this->container->bookmarkService->set($bookmark, $writeDatastore);
if (false === $this->container->loginManager->isLoggedIn()) {
return false;
}
return true;
// If thumbnail should be updated, we reset it to null
if ($bookmark->shouldUpdateThumbnail()) {
$bookmark->setThumbnail(null);
// Requires an update, not async retrieval, thumbnails enabled
if ($bookmark->shouldUpdateThumbnail()
&& true !== $this->container->conf->get('general.enable_async_metadata', true)
&& $this->container->conf->get('thumbnails.mode', Thumbnailer::MODE_NONE) !== Thumbnailer::MODE_NONE
) {
$bookmark->setThumbnail($this->container->thumbnailer->get($bookmark->getUrl()));
$this->container->bookmarkService->set($bookmark, $writeDatastore);
return true;
}
}
return false;

View file

@ -53,6 +53,16 @@ class InstallController extends ShaarliVisitorController
$this->assignView('cities', $cities);
$this->assignView('languages', Languages::getAvailableLanguages());
$phpEol = new \DateTimeImmutable(ApplicationUtils::getPhpEol(PHP_VERSION));
$this->assignView('php_version', PHP_VERSION);
$this->assignView('php_eol', format_date($phpEol, false));
$this->assignView('php_has_reached_eol', $phpEol < new \DateTimeImmutable());
$this->assignView('php_extensions', ApplicationUtils::getPhpExtensionsRequirement());
$this->assignView('permissions', ApplicationUtils::checkResourcePermissions($this->container->conf));
$this->assignView('pagetitle', t('Install Shaarli'));
return $response->write($this->render('install'));
}
@ -150,7 +160,7 @@ class InstallController extends ShaarliVisitorController
protected function checkPermissions(): bool
{
// Ensure Shaarli has proper access to its resources
$errors = ApplicationUtils::checkResourcePermissions($this->container->conf);
$errors = ApplicationUtils::checkResourcePermissions($this->container->conf, true);
if (empty($errors)) {
return true;
}