From 6e0d16f22b94bb528185d16d61c2ed93de38fcbd Mon Sep 17 00:00:00 2001 From: Philipp Date: Sat, 7 Jan 2023 15:16:55 +0100 Subject: [PATCH] Add warning message in case node.config.php isn't writable --- src/Core/Config/Util/ConfigFileManager.php | 27 ++++++++++++++++++++-- src/DI.php | 5 ++++ src/Module/Admin/Summary.php | 5 ++++ 3 files changed, 35 insertions(+), 2 deletions(-) diff --git a/src/Core/Config/Util/ConfigFileManager.php b/src/Core/Config/Util/ConfigFileManager.php index f9d3b32b64..8705bf76e7 100644 --- a/src/Core/Config/Util/ConfigFileManager.php +++ b/src/Core/Config/Util/ConfigFileManager.php @@ -218,6 +218,22 @@ class ConfigFileManager } } + /** + * Checks, if the node.config.php is writable + * + * @return bool + */ + public function dataIsWritable(): bool + { + $filename = $this->configDir . '/' . self::CONFIG_DATA_FILE; + + if (file_exists($filename)) { + return is_writable($filename); + } else { + return is_writable($this->configDir); + } + } + /** * Saves overridden config entries back into the data.config.php * @@ -229,6 +245,11 @@ class ConfigFileManager { $filename = $this->configDir . '/' . self::CONFIG_DATA_FILE; + // fail at a early stage, if we already know that we cannot save the data + if (!$this->dataIsWritable()) { + throw new ConfigFileException(sprintf('Cannot open file "%s" in mode c+', $filename)); + } + if (file_exists($filename)) { $fileExists = true; } else { @@ -238,13 +259,15 @@ class ConfigFileManager /** * Creates a read-write stream * - * @see https://www.php.net/manual/en/function.fopen.php + * @see https://www.php.net/manual/en/function.fopen.php * @note Open the file for reading and writing. If the file does not exist, it is created. * If it exists, it is neither truncated (as opposed to 'w'), nor the call to this function fails * (as is the case with 'x'). The file pointer is positioned on the beginning of the file. * */ - $configStream = fopen($filename, 'c+'); + if (($configStream = @fopen($filename, 'c+')) !== false) { + throw new ConfigFileException(sprintf('Cannot open file "%s" in mode c+', $filename)); + } try { // We do want an exclusive lock, so we wait until every LOCK_SH (config reading) is unlocked diff --git a/src/DI.php b/src/DI.php index 0ef18a1aa3..6fd0e3a7ad 100644 --- a/src/DI.php +++ b/src/DI.php @@ -181,6 +181,11 @@ abstract class DI return self::$dice->create(Core\Config\Capability\IManageConfigValues::class); } + public static function configFileManager(): Core\Config\Util\ConfigFileManager + { + return self::$dice->create(Core\Config\Util\ConfigFileManager::class); + } + public static function keyValue(): Core\KeyValueStorage\Capabilities\IManageKeyValuePairs { return self::$dice->create(Core\KeyValueStorage\Capabilities\IManageKeyValuePairs::class); diff --git a/src/Module/Admin/Summary.php b/src/Module/Admin/Summary.php index 038628ee1e..325e392a18 100644 --- a/src/Module/Admin/Summary.php +++ b/src/Module/Admin/Summary.php @@ -23,6 +23,7 @@ namespace Friendica\Module\Admin; use Friendica\App; use Friendica\Core\Addon; +use Friendica\Core\Config\Util\ConfigFileManager; use Friendica\Core\Config\ValueObject\Cache; use Friendica\Core\Logger; use Friendica\Core\Renderer; @@ -114,6 +115,10 @@ class Summary extends BaseAdmin $warningtext[] = DI::l10n()->t('Friendica\'s configuration now is stored in config/local.config.php, please copy config/local-sample.config.php and move your config from config/local.ini.php. See the Config help page for help with the transition.', DI::baseUrl()->get() . '/help/Config'); } + if (!DI::configFileManager()->dataIsWritable()) { + $warningtext[] = DI::l10n()->t('Friendica\'s configuration store "%s" isn\'t writable. Beware that updates, gui changes and console changes aren\'t working reliable.', ConfigFileManager::CONFIG_DATA_FILE); + } + // Check server vitality if (!self::checkSelfHostMeta()) { $well_known = DI::baseUrl()->get() . Probe::HOST_META;